# http://linux.bkbits.net:8080/linux-2.4/gnupatch@3ff8697bFIYfsvIbsqw27h6C_rbCEA
# http://cve.mitre.org/cgi-bin/cvename.cgi?name=CAN-2003-0984
# http://www.ultramonkey.org/bugs/cve/CAN-2003-0984.shtml

# This is a BitKeeper generated diff -Nru style patch.
#
# ChangeSet
#   2004/01/04 17:28:59-02:00 trini@mvista.com 
#   [PATCH] /dev/rtc can leak parts of kernel memory to unpriviledged users
#   
#   ===== arch/cris/drivers/ds1302.c 1.6 vs edited =====
# 
# arch/cris/drivers/ds1302.c
#   2003/10/24 08:34:36-02:00 trini@mvista.com +1 -0
#   Fix /dev/rtc leak
# 
# arch/cris/drivers/pcf8563.c
#   2003/10/24 08:34:36-02:00 trini@mvista.com +1 -0
#   Fix /dev/rtc leak
# 
# arch/m68k/bvme6000/rtc.c
#   2003/10/24 08:34:36-02:00 trini@mvista.com +1 -0
#   Fix /dev/rtc leak
# 
# arch/m68k/mvme16x/rtc.c
#   2003/10/24 08:34:37-02:00 trini@mvista.com +1 -0
#   Fix /dev/rtc leak
# 
# arch/ppc64/kernel/rtc.c
#   2003/10/24 08:34:37-02:00 trini@mvista.com +1 -0
#   Fix /dev/rtc leak
# 
# drivers/acorn/char/i2c.c
#   2003/10/24 08:34:37-02:00 trini@mvista.com +1 -0
#   Fix /dev/rtc leak
# 
# drivers/char/ds1286.c
#   2003/10/24 08:34:37-02:00 trini@mvista.com +2 -1
#   Fix /dev/rtc leak
# 
# drivers/char/efirtc.c
#   2003/10/24 08:35:10-02:00 trini@mvista.com +1 -0
#   Fix /dev/rtc leak
# 
# drivers/char/ip27-rtc.c
#   2003/10/24 08:34:38-02:00 trini@mvista.com +1 -0
#   Fix /dev/rtc leak
# 
# drivers/char/mips_rtc.c
#   2003/10/24 08:34:38-02:00 trini@mvista.com +1 -0
#   Fix /dev/rtc leak
# 
# drivers/char/rtc.c
#   2003/10/24 08:34:38-02:00 trini@mvista.com +2 -1
#   Fix /dev/rtc leak
# 
# drivers/hil/hp_sdc_rtc.c
#   2003/10/24 08:34:39-02:00 trini@mvista.com +2 -0
#   Fix /dev/rtc leak
# 
# drivers/macintosh/rtc.c
#   2003/10/24 08:34:39-02:00 trini@mvista.com +1 -0
#   Fix /dev/rtc leak
# 
# drivers/sbus/char/rtc.c
#   2003/10/24 08:34:39-02:00 trini@mvista.com +1 -0
#   Fix /dev/rtc leak
# 
diff -Nru a/arch/cris/drivers/ds1302.c b/arch/cris/drivers/ds1302.c
--- a/arch/cris/drivers/ds1302.c	2004-06-14 04:15:14 -07:00
+++ b/arch/cris/drivers/ds1302.c	2004-06-14 04:15:14 -07:00
@@ -346,6 +346,7 @@
 		{
 			struct rtc_time rtc_tm;
 						
+			memset(&rtc_tm, 0, sizeof (struct rtc_time));
 			get_rtc_time(&rtc_tm);						
 			if (copy_to_user((struct rtc_time*)arg, &rtc_tm, sizeof(struct rtc_time)))
 				return -EFAULT;	
diff -Nru a/arch/cris/drivers/pcf8563.c b/arch/cris/drivers/pcf8563.c
--- a/arch/cris/drivers/pcf8563.c	2004-06-14 04:15:14 -07:00
+++ b/arch/cris/drivers/pcf8563.c	2004-06-14 04:15:14 -07:00
@@ -220,6 +220,7 @@
 		{
 			struct rtc_time tm;
 
+			memset(&tm, 0, sizeof (struct rtc_time));
 			get_rtc_time(&tm);
 
 			if (copy_to_user((struct rtc_time *) arg, &tm, sizeof tm)) {
diff -Nru a/arch/m68k/bvme6000/rtc.c b/arch/m68k/bvme6000/rtc.c
--- a/arch/m68k/bvme6000/rtc.c	2004-06-14 04:15:14 -07:00
+++ b/arch/m68k/bvme6000/rtc.c	2004-06-14 04:15:14 -07:00
@@ -54,6 +54,7 @@
 		/* Ensure clock and real-time-mode-register are accessible */
 		msr = rtc->msr & 0xc0;
 		rtc->msr = 0x40;
+		memset(&wtime, 0, sizeof(struct rtc_time));
 		do {
 			wtime.tm_sec =  BCD2BIN(rtc->bcd_sec);
 			wtime.tm_min =  BCD2BIN(rtc->bcd_min);
diff -Nru a/arch/m68k/mvme16x/rtc.c b/arch/m68k/mvme16x/rtc.c
--- a/arch/m68k/mvme16x/rtc.c	2004-06-14 04:15:14 -07:00
+++ b/arch/m68k/mvme16x/rtc.c	2004-06-14 04:15:14 -07:00
@@ -52,6 +52,7 @@
 		cli();
 		/* Ensure clock and real-time-mode-register are accessible */
 		rtc->ctrl = RTC_READ;
+		memset(&wtime, 0, sizeof(struct rtc_time));
 		wtime.tm_sec =  BCD2BIN(rtc->bcd_sec);
 		wtime.tm_min =  BCD2BIN(rtc->bcd_min);
 		wtime.tm_hour = BCD2BIN(rtc->bcd_hr);
diff -Nru a/arch/ppc64/kernel/rtc.c b/arch/ppc64/kernel/rtc.c
--- a/arch/ppc64/kernel/rtc.c	2004-06-14 04:15:14 -07:00
+++ b/arch/ppc64/kernel/rtc.c	2004-06-14 04:15:14 -07:00
@@ -96,6 +96,7 @@
 	switch (cmd) {
 	case RTC_RD_TIME:	/* Read the time/date from RTC	*/
 	{
+		memset(&wtime, 0, sizeof(struct rtc_time));
 		ppc_md.get_rtc_time(&wtime);
 		break;
 	}
diff -Nru a/drivers/acorn/char/i2c.c b/drivers/acorn/char/i2c.c
--- a/drivers/acorn/char/i2c.c	2004-06-14 04:15:14 -07:00
+++ b/drivers/acorn/char/i2c.c	2004-06-14 04:15:14 -07:00
@@ -166,6 +166,7 @@
 		break;
 
 	case RTC_RD_TIME:
+		memset(&rtctm, 0, sizeof(struct rtc_time));
 		get_rtc_time(&rtc_raw, &year);
 		rtctm.tm_sec  = rtc_raw.secs;
 		rtctm.tm_min  = rtc_raw.mins;
diff -Nru a/drivers/char/ds1286.c b/drivers/char/ds1286.c
--- a/drivers/char/ds1286.c	2004-06-14 04:15:14 -07:00
+++ b/drivers/char/ds1286.c	2004-06-14 04:15:14 -07:00
@@ -173,7 +173,7 @@
 		 * means "don't care" or "match all". Only the tm_hour,
 		 * tm_min, and tm_sec values are filled in.
 		 */
-
+		memset(&wtime, 0, sizeof(struct rtc_time));
 		ds1286_get_alm_time(&wtime);
 		break;
 	}
@@ -216,6 +216,7 @@
 	}
 	case RTC_RD_TIME:	/* Read the time/date from RTC	*/
 	{
+		memset(&wtime, 0, sizeof(struct rtc_time));
 		ds1286_get_time(&wtime);
 		break;
 	}
diff -Nru a/drivers/char/efirtc.c b/drivers/char/efirtc.c
--- a/drivers/char/efirtc.c	2004-06-14 04:15:14 -07:00
+++ b/drivers/char/efirtc.c	2004-06-14 04:15:14 -07:00
@@ -118,6 +118,7 @@
 static void
 convert_from_efi_time(efi_time_t *eft, struct rtc_time *wtime)
 {
+	memset(&wtime, 0, sizeof(struct rtc_time));
 	wtime->tm_sec  = eft->second;
 	wtime->tm_min  = eft->minute;
 	wtime->tm_hour = eft->hour;
diff -Nru a/drivers/char/ip27-rtc.c b/drivers/char/ip27-rtc.c
--- a/drivers/char/ip27-rtc.c	2004-06-14 04:15:14 -07:00
+++ b/drivers/char/ip27-rtc.c	2004-06-14 04:15:14 -07:00
@@ -83,6 +83,7 @@
 	switch (cmd) {
 	case RTC_RD_TIME:	/* Read the time/date from RTC	*/
 	{
+		memset(&wtime, 0, sizeof(struct rtc_time));
 		get_rtc_time(&wtime);
 		break;
 	}
diff -Nru a/drivers/char/mips_rtc.c b/drivers/char/mips_rtc.c
--- a/drivers/char/mips_rtc.c	2004-06-14 04:15:14 -07:00
+++ b/drivers/char/mips_rtc.c	2004-06-14 04:15:14 -07:00
@@ -82,6 +82,7 @@
 
 	switch (cmd) {
 	case RTC_RD_TIME:	/* Read the time/date from RTC  */
+		memset(&rtc_tm, 0, sizeof(struct rtc_time));
 		curr_time = rtc_get_time();
 		to_tm(curr_time, &rtc_tm);
 		rtc_tm.tm_year -= 1900;
diff -Nru a/drivers/char/rtc.c b/drivers/char/rtc.c
--- a/drivers/char/rtc.c	2004-06-14 04:15:14 -07:00
+++ b/drivers/char/rtc.c	2004-06-14 04:15:14 -07:00
@@ -362,7 +362,7 @@
 		 * means "don't care" or "match all". Only the tm_hour,
 		 * tm_min, and tm_sec values are filled in.
 		 */
-
+		memset(&wtime, 0, sizeof(struct rtc_time));
 		get_rtc_alm_time(&wtime);
 		break; 
 	}
@@ -406,6 +406,7 @@
 	}
 	case RTC_RD_TIME:	/* Read the time/date from RTC	*/
 	{
+		memset(&wtime, 0, sizeof(struct rtc_time));
 		get_rtc_time(&wtime);
 		break;
 	}
diff -Nru a/drivers/hil/hp_sdc_rtc.c b/drivers/hil/hp_sdc_rtc.c
--- a/drivers/hil/hp_sdc_rtc.c	2004-06-14 04:15:14 -07:00
+++ b/drivers/hil/hp_sdc_rtc.c	2004-06-14 04:15:14 -07:00
@@ -561,6 +561,7 @@
         }
         case RTC_ALM_READ:      /* Read the present alarm time */
         {
+		memset(&ttime, 0, sizeof(struct timeval));
 		if (hp_sdc_rtc_read_mt(&ttime)) return -EFAULT;
                 break;
         }
@@ -609,6 +610,7 @@
         }
         case RTC_RD_TIME:       /* Read the time/date from RTC  */
         {
+		memset(&wtime, 0, sizeof(struct rtc_time));
 		if (hp_sdc_rtc_read_bbrtc(&wtime)) return -EFAULT;
                 break;
         }
diff -Nru a/drivers/macintosh/rtc.c b/drivers/macintosh/rtc.c
--- a/drivers/macintosh/rtc.c	2004-06-14 04:15:14 -07:00
+++ b/drivers/macintosh/rtc.c	2004-06-14 04:15:14 -07:00
@@ -64,6 +64,7 @@
 	case RTC_RD_TIME:
 		if (ppc_md.get_rtc_time)
 		{
+			memset(&rtc_tm, 0, sizeof(struct rtc_time));
 			get_rtc_time(&rtc_tm);
 
 			if (copy_to_user((struct rtc_time*)arg, &rtc_tm, sizeof(struct rtc_time)))
diff -Nru a/drivers/sbus/char/rtc.c b/drivers/sbus/char/rtc.c
--- a/drivers/sbus/char/rtc.c	2004-06-14 04:15:14 -07:00
+++ b/drivers/sbus/char/rtc.c	2004-06-14 04:15:14 -07:00
@@ -89,6 +89,7 @@
 	switch (cmd)
 	{
 	case RTCGET:
+		memset(&rtc_tm, 0, sizeof(struct rtc_time));
 		get_rtc_time(&rtc_tm);
 
 		if (copy_to_user((struct rtc_time*)arg, &rtc_tm, sizeof(struct rtc_time)))
