aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorroot <root@artemis.panaceas.org>2017-01-16 14:08:05 +0000
committerroot <root@artemis.panaceas.org>2017-01-16 14:08:05 +0000
commit71a5a65d090cd71cabfb3fc94209d621d5a9fd0b (patch)
tree1cc85edd1f3a741dd5bbc737bb7ad96e1d97a405
parent3906adfa968f54c93ffffc6fc31f34aca2517c61 (diff)
downloadtwa_t-71a5a65d090cd71cabfb3fc94209d621d5a9fd0b.tar.gz
twa_t-71a5a65d090cd71cabfb3fc94209d621d5a9fd0b.tar.bz2
twa_t-71a5a65d090cd71cabfb3fc94209d621d5a9fd0b.zip
add patch
-rw-r--r--README.html4
-rw-r--r--kernel-patch/twa-time.patch130
2 files changed, 134 insertions, 0 deletions
diff --git a/README.html b/README.html
index 284c11b..2aa463d 100644
--- a/README.html
+++ b/README.html
@@ -28,3 +28,7 @@ Controller time is: Sun Jan 16 12:29:55 2017
root@otherthing:~/projects/twa_t/twa_t/src#
</pre>
+<p>
+A kernel patch which does much the same thing is included in the directory kernel-patch
+</p>
+
diff --git a/kernel-patch/twa-time.patch b/kernel-patch/twa-time.patch
new file mode 100644
index 0000000..79c6290
--- /dev/null
+++ b/kernel-patch/twa-time.patch
@@ -0,0 +1,130 @@
+Sync 3ware time at boot to system rtc
+
+diff --git a/drivers/scsi/3w-9xxx.c b/drivers/scsi/3w-9xxx.c
+index cd4129f..28952c6 100644
+--- a/drivers/scsi/3w-9xxx.c
++++ b/drivers/scsi/3w-9xxx.c
+@@ -91,6 +91,7 @@
+ #include <linux/delay.h>
+ #include <linux/pci.h>
+ #include <linux/time.h>
++#include <linux/rtc.h>
+ #include <linux/mutex.h>
+ #include <linux/slab.h>
+ #include <asm/io.h>
+@@ -462,6 +464,93 @@ out:
+ return retval;
+ } /* End twa_aen_severity_lookup() */
+
++static void twa_time(u8 *buf)
++{
++ struct timeval utc;
++ u64 local_time;
++ struct rtc_time tm;
++ u16 year;
++
++ do_gettimeofday(&utc);
++ local_time = (u64)(utc.tv_sec - (sys_tz.tz_minuteswest * 60));
++
++ rtc_time64_to_tm(local_time, &tm);
++
++
++ buf[0] = 0x00; /* Unknown always reads 0 */
++ buf[1] = tm.tm_sec;
++ buf[2] = tm.tm_min;
++ buf[3] = tm.tm_hour;
++
++ buf[4] = tm.tm_mday;
++ buf[5] = tm.tm_mon + 1;
++
++ year = cpu_to_le16(tm.tm_year + 1900);
++ memcpy(&buf[6], &year, sizeof(year));
++}
++
++static void *twa_get_param(TW_Device_Extension *tw_dev, int request_id, int table_id, int parameter_id, int parameter_size_bytes);
++
++
++static void twa_print_date_time(TW_Device_Extension *tw_dev, int request_id)
++{
++ u8 *buf=twa_get_param(tw_dev,1,TW_TIMEKEEP_TABLE,0x4,0x8);
++ u16 year;
++
++ if (!buf) {
++ printk(KERN_WARNING "3w-9xxx: scsi%d: WARNING: Can't read controller date and time\n",
++ tw_dev->host->host_no);
++ return;
++ }
++
++ memcpy(&year, &buf[6], sizeof(year));
++
++ year = le16_to_cpu(year);
++
++ printk(KERN_WARNING "3w-9xxx: scsi%d: controller time %02d-%02d-%04d %02d:%02d:%02d\n",
++ tw_dev->host->host_no,
++ (int) buf[4],
++ (int) buf[5],
++ (int) year,
++ (int) buf[3],
++ (int) buf[2],
++ (int) buf[1]);
++}
++
++/* This function will sync firmware time with the host time */
++static void twa_aen_sync_date_time(TW_Device_Extension *tw_dev, int request_id)
++{
++ TW_Command_Full *full_command_packet;
++ TW_Command *command_packet;
++ TW_Param_Apache *param;
++ /* Fill out the command packet */
++ full_command_packet = tw_dev->command_packet_virt[request_id];
++ memset(full_command_packet, 0, sizeof(TW_Command_Full));
++ command_packet = &full_command_packet->command.oldcommand;
++ command_packet->opcode__sgloffset = TW_OPSGL_IN(2, TW_OP_SET_PARAM);
++ command_packet->request_id = request_id;
++ command_packet->byte8_offset.param.sgl[0].address = TW_CPU_TO_SGL(tw_dev->generic_buffer_phys[request_id]);
++ command_packet->byte8_offset.param.sgl[0].length = cpu_to_le32(TW_SECTOR_SIZE);
++ command_packet->size = TW_COMMAND_SIZE;
++ command_packet->byte6_offset.parameter_count = cpu_to_le16(1);
++
++ /* Setup the param */
++ param = (TW_Param_Apache *)tw_dev->generic_buffer_virt[request_id];
++ memset(param, 0, TW_SECTOR_SIZE);
++ param->table_id = cpu_to_le16(TW_TIMEKEEP_TABLE | 0x8000); /* Controller time keep table */
++ param->parameter_id = cpu_to_le16(0x4); /* SchedulerTime */
++ param->parameter_size_bytes = cpu_to_le16(8);
++
++ twa_time(param->data);
++
++ /* Mark internal command */
++ tw_dev->srb[request_id] = NULL;
++
++ /* Now post the command */
++ twa_post_command_packet(tw_dev, request_id, 1);
++} /* End twa_aen_sync_date_time() */
++
++
+ /* This function will sync firmware time with the host time */
+ static void twa_aen_sync_time(TW_Device_Extension *tw_dev, int request_id)
+ {
+@@ -2121,6 +2210,21 @@ static int twa_probe(struct pci_dev *pdev, const struct pci_device_id *dev_id)
+ le32_to_cpu(*(int *)twa_get_param(tw_dev, 2, TW_INFORMATION_TABLE,
+ TW_PARAM_PORTCOUNT, TW_PARAM_PORTCOUNT_LENGTH)));
+
++ twa_print_date_time(tw_dev, 0);
++
++ /* Set clock */
++ twa_aen_sync_date_time(tw_dev, 0);
++
++ /* Poll for completion */
++ if (twa_poll_response(tw_dev, 0, 30))
++ printk(KERN_WARNING "3w-9xxx: scsi%d: no response to set time\n",
++ host->host_no);
++ else
++ printk(KERN_WARNING "3w-9xxx: scsi%d: setting clock\n",
++ host->host_no);
++
++ twa_print_date_time(tw_dev, 0);
++
+ /* Try to enable MSI */
+ if (use_msi && (pdev->device != PCI_DEVICE_ID_3WARE_9000) &&
+ !pci_enable_msi(pdev))