Index: include/ipmitool/ipmi_sdr.h
===================================================================
RCS file: /cvsroot/ipmitool/ipmitool/include/ipmitool/ipmi_sdr.h,v
retrieving revision 1.39
diff -c -r1.39 ipmi_sdr.h
*** include/ipmitool/ipmi_sdr.h	11 Jul 2007 14:27:45 -0000	1.39
--- include/ipmitool/ipmi_sdr.h	12 Nov 2008 22:29:59 -0000
***************
*** 154,159 ****
--- 154,162 ----
  	uint8_t length;		/* remaining record bytes */
  } __attribute__ ((packed));
  
+ #define ENTER_SDRR_UPDATE_MODE  0x2A
+ #define EXIT_SDRR_UPDATE_MODE  0x2B
+ 
  struct sdr_record_mask {
  	union {
  		struct {
Index: lib/ipmi_gendev.c
===================================================================
RCS file: /cvsroot/ipmitool/ipmitool/lib/ipmi_gendev.c,v
retrieving revision 1.1
diff -c -r1.1 ipmi_gendev.c
*** lib/ipmi_gendev.c	17 Sep 2008 20:00:53 -0000	1.1
--- lib/ipmi_gendev.c	12 Nov 2008 22:29:59 -0000
***************
*** 42,47 ****
--- 42,48 ----
  #include <ipmitool/log.h>
  #include <ipmitool/ipmi_mc.h>
  #include <ipmitool/ipmi_sdr.h>
+ #include <ipmitool/ipmi_raw.h>
  #include <ipmitool/ipmi_gendev.h>
  #include <ipmitool/ipmi_intf.h>
  #include <ipmitool/ipmi_sel.h>
Index: lib/ipmi_sdr.c
===================================================================
RCS file: /cvsroot/ipmitool/ipmitool/lib/ipmi_sdr.c,v
retrieving revision 1.84
diff -c -r1.84 ipmi_sdr.c
*** lib/ipmi_sdr.c	9 Jul 2008 05:55:55 -0000	1.84
--- lib/ipmi_sdr.c	12 Nov 2008 22:30:00 -0000
***************
*** 4231,4237 ****
  		lprintf(LOG_ERR, "               dump <file>");
  		lprintf(LOG_ERR,
  			"                     Dump raw SDR data to a file");
! 		lprintf(LOG_ERR, "               fill");
  		lprintf(LOG_ERR,
  			"                     sensors       Creates the SDR repository for the current configuration");
  		lprintf(LOG_ERR,
--- 4231,4237 ----
  		lprintf(LOG_ERR, "               dump <file>");
  		lprintf(LOG_ERR,
  			"                     Dump raw SDR data to a file");
! 		lprintf(LOG_ERR, "               fill [updatemode]");
  		lprintf(LOG_ERR,
  			"                     sensors       Creates the SDR repository for the current configuration");
  		lprintf(LOG_ERR,
***************
*** 4285,4302 ****
  		else
  			rc = ipmi_sdr_dump_bin(intf, argv[1]);
  	} else if (strncmp(argv[0], "fill", 4) == 0) {
! 		if (argc <= 1) {
! 			lprintf(LOG_ERR, "usage: sdr fill sensors");
! 			lprintf(LOG_ERR, "usage: sdr fill file <filename>");
  			rc = -1;
! 		} else if (strncmp(argv[1], "sensors", 7) == 0) {
! 			rc = ipmi_sdr_add_from_sensors(intf, 21);
! 		} else if (strncmp(argv[1], "file", 4) == 0) {
  			if (argc < 3) {
  				lprintf(LOG_ERR, "sdr fill: Missing filename");
  				rc = -1;
  			} else {
! 				rc = ipmi_sdr_add_from_file(intf, argv[2]);
  			}
  		}
  	} else {
--- 4285,4308 ----
  		else
  			rc = ipmi_sdr_dump_bin(intf, argv[1]);
  	} else if (strncmp(argv[0], "fill", 4) == 0) {
! 		int updatemode = 0;
! 		int arg_offset = 1;
! 		if (argc >= 2 && !strncmp(argv[1], "updatemode", 10)) {
! 			updatemode = 1;
! 			arg_offset = 2;
! 		}
! 		if (argc <= arg_offset) {
! 			lprintf(LOG_ERR, "usage: sdr fill [updatemode] sensors");
! 			lprintf(LOG_ERR, "usage: sdr fill [updatemode] file <filename>");
  			rc = -1;
! 		} else if (strncmp(argv[arg_offset], "sensors", 7) == 0) {
! 			rc = ipmi_sdr_add_from_sensors(intf, 21, updatemode);
! 		} else if (strncmp(argv[arg_offset], "file", 4) == 0) {
  			if (argc < 3) {
  				lprintf(LOG_ERR, "sdr fill: Missing filename");
  				rc = -1;
  			} else {
! 				rc = ipmi_sdr_add_from_file(intf, argv[arg_offset+1], updatemode);
  			}
  		}
  	} else {
Index: lib/ipmi_sdradd.c
===================================================================
RCS file: /cvsroot/ipmitool/ipmitool/lib/ipmi_sdradd.c,v
retrieving revision 1.1
diff -c -r1.1 ipmi_sdradd.c
*** lib/ipmi_sdradd.c	11 Jul 2007 14:27:46 -0000	1.1
--- lib/ipmi_sdradd.c	12 Nov 2008 22:30:00 -0000
***************
*** 62,68 ****
    uint8_t data[1];      /* SDR record data */
  } __attribute__ ((packed));
  
! static int sdr_max_write_len = 24;
  
  static int
  partial_send(struct ipmi_intf *intf, struct ipmi_rq *req, uint16_t *id)
--- 62,69 ----
    uint8_t data[1];      /* SDR record data */
  } __attribute__ ((packed));
  
! // Safe maximum per spec is 19 (32 - (6+6+1)), but we'll be conservative
! static int sdr_max_write_len = 16;
  
  static int
  partial_send(struct ipmi_intf *intf, struct ipmi_rq *req, uint16_t *id)
***************
*** 205,210 ****
--- 206,253 ----
    return -1;
  }
  
+ static int
+ ipmi_sdr_enter_update_mode(struct ipmi_intf *intf)
+ {
+   struct ipmi_rs *rsp;
+   struct ipmi_rq req;
+   uint8_t msg_data[8];
+ 
+   memset(&req, 0, sizeof(req));
+   req.msg.netfn = IPMI_NETFN_STORAGE;
+   req.msg.cmd = ENTER_SDRR_UPDATE_MODE;
+   req.msg.data = msg_data;
+   req.msg.data_len = 0;
+ 
+   rsp = intf->sendrecv(intf, &req);
+   if (rsp == NULL) {
+     lprintf(LOG_ERR, "Unable to enter SDRR Update Mode");
+     return -1;
+   }
+   return 0;
+ }
+ 
+ static int
+ ipmi_sdr_exit_update_mode(struct ipmi_intf *intf)
+ {
+   struct ipmi_rs *rsp;
+   struct ipmi_rq req;
+   uint8_t msg_data[8];
+ 
+   memset(&req, 0, sizeof(req));
+   req.msg.netfn = IPMI_NETFN_STORAGE;
+   req.msg.cmd = EXIT_SDRR_UPDATE_MODE;
+   req.msg.data = msg_data;
+   req.msg.data_len = 0;
+ 
+   rsp = intf->sendrecv(intf, &req);
+   if (rsp == NULL) {
+     lprintf(LOG_ERR, "Unable to enter SDRR Update Mode");
+     return -1;
+   }
+   return 0;
+ }
+ 
  
  struct sdrr_queue {
    struct sdr_record_list *head;
***************
*** 288,300 ****
  }
  
  int
! ipmi_sdr_add_from_sensors(struct ipmi_intf *intf, int maxslot)
  {
    int i;
    int rc = 0;
    int slave_addr;
    int myaddr = intf->target_addr;
  
    if (ipmi_sdr_repo_clear(intf)) {
      lprintf(LOG_ERR, "Cannot erase SDRR. Give up.");
      return -1;
--- 331,348 ----
  }
  
  int
! ipmi_sdr_add_from_sensors(struct ipmi_intf *intf, int maxslot, int updatemode)
  {
    int i;
    int rc = 0;
    int slave_addr;
    int myaddr = intf->target_addr;
  
+   if (updatemode && ipmi_sdr_enter_update_mode(intf)) {
+     lprintf(LOG_ERR, "Cannot enter SDR Repository Upate Mode. Give up.");
+     return -1;
+   }
+ 
    if (ipmi_sdr_repo_clear(intf)) {
      lprintf(LOG_ERR, "Cannot erase SDRR. Give up.");
      return -1;
***************
*** 312,317 ****
--- 360,371 ----
        rc = -1;
      }
    }
+ 
+   if (updatemode && ipmi_sdr_exit_update_mode(intf)) {
+     lprintf(LOG_ERR, "Cannot Exit SDR Repository Upate Mode.");
+     rc = -1;
+   }
+ 
    return rc;
  }
  
***************
*** 383,389 ****
  }
  
  int
! ipmi_sdr_add_from_file(struct ipmi_intf *intf, const char *ifile)
  {
    int rc;
    struct sdrr_queue sdrr_queue;
--- 437,443 ----
  }
  
  int
! ipmi_sdr_add_from_file(struct ipmi_intf *intf, const char *ifile, int updatemode)
  {
    int rc;
    struct sdrr_queue sdrr_queue;
***************
*** 393,398 ****
--- 447,457 ----
    /* read the SDR records from file */
    rc = ipmi_sdr_read_records(ifile, &sdrr_queue);
  
+   if (updatemode && ipmi_sdr_enter_update_mode(intf)) {
+     lprintf(LOG_ERR, "Cannot enter SDR Repository Upate Mode. Give up.");
+     return -1;
+   }
+ 
    if (ipmi_sdr_repo_clear(intf)) {
      printf("Cannot erase SDRR. Give up.\n");
      /* FIXME: free sdr list */
***************
*** 408,413 ****
--- 467,478 ----
      }
      free(sdrr);
    }
+ 
+   if (updatemode && ipmi_sdr_exit_update_mode(intf)) {
+     lprintf(LOG_ERR, "Cannot Exit SDR Repository Upate Mode.");
+     rc = -1;
+   }
+ 
    return rc;
  }
  
