[Tinyos-contrib-commits] CVS: tinyos-1.x/contrib/imote2/tos/sensorboards/Framework SensorboardFrameworkC.nc, NONE, 1.1 SensorboardFrameworkM.nc, NONE, 1.1 BoardManager.nc, 1.1, 1.2 ChannelManager.nc, 1.1, 1.2 ChannelManagerM.nc, 1.1, 1.2 ChannelParamsManagerM.nc, 1.1, 1.2 SensorData.nc, 1.1, 1.2 TriggerManager.nc, 1.1, 1.2 TriggerManagerM.nc, 1.1, 1.2 sensorTypes.h, 1.1, 1.2

Lama Nachman lnachman at users.sourceforge.net
Sun Mar 4 23:29:22 PST 2007


Update of /cvsroot/tinyos/tinyos-1.x/contrib/imote2/tos/sensorboards/Framework
In directory sc8-pr-cvs10.sourceforge.net:/tmp/cvs-serv1178/Framework

Modified Files:
	BoardManager.nc ChannelManager.nc ChannelManagerM.nc 
	ChannelParamsManagerM.nc SensorData.nc TriggerManager.nc 
	TriggerManagerM.nc sensorTypes.h 
Added Files:
	SensorboardFrameworkC.nc SensorboardFrameworkM.nc 
Log Message:
Pushed out internal tree


--- NEW FILE: SensorboardFrameworkC.nc ---
/**
*
*@author Robbie Adler
*
**/

configuration SensorboardFrameworkC{
    provides {
      interface StdControl;
      interface GenericSampling;
    }
    uses{
      interface BufferManagement;
      interface WriteData;
      interface SensorData[uint8_t dataChannel];
      interface DSPManager[uint8_t dataChannel];
      interface BoardManager;
    }
}

implementation {
#include "frameworkconfig.h"

  components SensorboardFrameworkM,
    Main,
    PXA27XWallClockM,
    TimerC,
    TriggerManagerM,
    ChannelManagerM,
    BufferManagementDispatchM,
#ifdef BLUSH_TRIGGER
    BluSHC,
#endif
#ifdef USE_UNIQUE_SEQUENCE_ID
    UniqueSequenceIDC,
#endif
    ChannelParamsManagerM;
    
    
  StdControl = SensorboardFrameworkM.StdControl;
  GenericSampling = SensorboardFrameworkM;
  
  SensorboardFrameworkM.DependentControl -> ChannelManagerM.StdControl;
  SensorboardFrameworkM.DependentControl -> ChannelParamsManagerM.StdControl;
  SensorboardFrameworkM.DependentControl -> TriggerManagerM.StdControl;

  SensorboardFrameworkM.ChannelManager -> ChannelManagerM;
  ChannelManagerM.TriggerManager -> TriggerManagerM;  
  ChannelManagerM.ChannelParamsManager -> ChannelParamsManagerM;
  
  
  BoardManager  = ChannelManagerM.BoardManager;
  DSPManager = ChannelManagerM.DSPManager;
  SensorData = TriggerManagerM.SensorData;
  BufferManagement =  BufferManagementDispatchM.OutsideBufferManagement;
  TriggerManagerM.BufferManagement-> BufferManagementDispatchM.InsideBufferManagement;
  ChannelManagerM.BufferManagement-> BufferManagementDispatchM.InsideBufferManagement;
  WriteData = ChannelManagerM;
      
  ChannelManagerM.ADCWarmupTimer -> TimerC.Timer[unique("Timer")];
  SensorboardFrameworkM.AcquisitionTimeout -> TimerC.Timer[unique("Timer")];
  
  ChannelManagerM.WallClock -> PXA27XWallClockM;
  Main.StdControl -> PXA27XWallClockM.StdControl;

#ifdef USE_UNIQUE_SEQUENCE_ID
  ChannelManagerM.UniqueSequenceID ->UniqueSequenceIDC.UniqueSequenceID;
  ChannelManagerM.UniqueSequenceIDControl ->UniqueSequenceIDC.StdControl;
#endif
  
  //-----------
  //BluSH commands
  
#ifdef BLUSH_TRIGGER
  BluSHC.BluSH_AppI[unique("BluSH")] -> TriggerManagerM.ForceTrigger;
#endif
}

--- NEW FILE: SensorboardFrameworkM.nc ---
includes downsample;
includes sensorboard;

module SensorboardFrameworkM{
  provides {
    interface StdControl;
    interface GenericSampling;
  }
  uses {
    interface SSP;
    interface Timer as AcquisitionTimeout;
    interface ChannelManager;
    
    interface StdControl as DependentControl;
  }
}
implementation {

#include "frameworkconfig.h"
#include "paramtask.h"

  result_t acquisitionDone(float scale);
  result_t triggerADCAcquisition();
  result_t doADCAcquisition();
  result_t cleanupSamplingState();
  result_t cleanupTimers();
 
  // paramaterized tasks
  
  void postPrepareDone(uint32_t arg);
  DEFINE_PARAMTASK(postPrepareDone);

  void postPrepareDoneFail(uint32_t arg);
  DEFINE_PARAMTASK(postPrepareDoneFail);

  void printList(char *header, uint8_t numItems, uint8_t* list) __attribute__ ((C,spontaneous));
  
  void printList(char *header, uint8_t numItems, uint8_t* list){
    char *buffer, tempBuf[8];
    buffer = malloc(256);
    
    if(buffer){
      int i, currentPos, currentCount;
      if(strlen(header) < 256){
	memcpy(buffer, header, strlen(header));
      }
      else{
	return;
      }
      currentPos = strlen(header);
      for(i=0; i<numItems; i++){
	currentCount = snprintf(tempBuf,8,"%d ",list[i]);
	if((currentCount > 0) && ((currentCount + currentPos) < 255)){
	  memcpy(buffer+currentPos,tempBuf, currentCount);
	  currentPos += currentCount;
	}
      }
      buffer[currentPos] = 0;
      trace(DBG_USR1,"%s\r\n",buffer);
      free(buffer);
    }
  }
  

#if 0   
  uint8_t *getNextBuffer(){
    int i;
    uint8_t *ret = NULL;
    atomic{
      for(i=0;i<NUMBUFFERS; i++){
	if(tempBuffers[i].inuse == FALSE){
	  tempBuffers[i].inuse = TRUE;
	  ret = (uint8_t *)tempBuffers[i].buf;
	  break;
	}
      }
    }
    return ret;
  }

  void returnBuffer(short *buf){
    int i;
    atomic{
      for(i=0;i<NUMBUFFERS; i++){
	if(tempBuffers[i].buf == buf){
	  tempBuffers[i].inuse = FALSE;
	}
      }
    }
  }
  
  void initBuffer(){
    int i;
    atomic{
      for(i=0;i<NUMBUFFERS; i++){
	tempBuffers[i].inuse = FALSE;
      }
    }
  }
#endif
    
  command result_t StdControl.init(){
      
    //    int i;

    trace(DBG_USR1,"\r\nInitializing %s\r\n", mySensorboardName);

#if 0
    initBuffer();
    atomic{
      //init global state that needs to be init'd
      gTotalTachTime=0;
      gTotalTachSamples=0;
      gLastTachValue=0;
      gSamplingInProgress = FALSE;
      for(i=0;i<MAX_SIMUL_CHANNELS;i++){
	gSampleInfo[i].sampleHeader.channelId = INVALID_CHANNEL_ID;
      }
      for(i=0;i<TOTAL_CHANNELS;i++){
	call GenericSampling.ClearTrigger(i);
      }
      
    }

    //SSP must be told whether it's Master or Slave to SCLK or SFRM and then
    //it can be inited.  All other parameters must be set after init is
    // called
    
    //read in our calibration values
#if EEPROM_PRESENT
    //read gVREFCal and gACCELCal out of the EEPROM
    //    call EEPROM.read(  );
    gVREFCal = 2.5;
    gACCELCal = 10.025;
#else
    gVREFCal = 2.5;
    gACCELCal = 10.025;
#endif
    
    //currently, this means that the board is not present
      
    gADCOffsetInt =0;
    gADCOffset = 0;
    gADCScale = 7.8920e-5;
    gADCAccelScale = 1.9e-4;
    gADCAccelDCScale = 5.024;
#endif

    call DependentControl.init();
    
    return SUCCESS;
  }
  
  command result_t StdControl.start(){
    
    call DependentControl.start();
    return SUCCESS;
  };

  command result_t StdControl.stop(){
    
    call DependentControl.stop();
    return SUCCESS;
  };
  
  event result_t AcquisitionTimeout.fired(){
    
    trace(DBG_USR1,"Acquisition Timeout\r\n");
    //we've timed out....
#if 0
    int i;
    bool samplingInProgress;
    
    atomic{
      samplingInProgress = gSamplingInProgress;
    }
    if(samplingInProgress == TRUE){
      
      //stop timers ASAP!!!
      cleanupTimers();
      
      trace(DBG_USR1,"ERROR:  GenericSampling Acquisition Timeout\r\n");
      
      //if we're still sampling....need to cleanup and notify
      for(i=0; i<MAX_SIMUL_CHANNELS; i++){
	if(gSampleInfo[i].sampleHeader.channelId!= INVALID_CHANNEL_ID){
	  //write the wrapperHeader and the sampleheader for this acquisitions
	  WRITEHEADER(gSampleInfo[i].dataBuffer,0,1);
	  WRITEHEADER(gSampleInfo[i].dataBuffer,4,WRAPPERHEADER_FIRSTOFFSET);
	  //set numSamples to 0 so that the sampleHeader is consistent with sampleBody.
	  gSampleInfo[i].sampleHeader.numSamples = 0;
	  memcpy(gSampleInfo[i].dataBuffer+WRAPPERHEADER_FIRSTOFFSET,
		 &(gSampleInfo[i].sampleHeader),
		 sizeof(sampleHeader_t));
	  	  
	  //do not support partial acquisitions because we have extremely
	  //limited insight into where we are at in the acquisition
	  
	  /*call WriteData.write(0, 
			       gSampleInfo[i].dataBuffer, 
			       sizeof(sampleHeader_t)+WRAPPERHEADER_FIRSTOFFSET);	
	  */
	  signal GenericSampling.samplingDone(gSampleInfo[i].sampleHeader.channelId,FAIL,0);  
	}
      }
      
      cleanupSamplingState();
      
    }
#endif
    return SUCCESS;
  }
  
  result_t cleanupTimers(){
    //this should work regardless of whether we have a timeout or not
    call AcquisitionTimeout.stop();
    return SUCCESS;
  }
  
  result_t cleanupSamplingState(){
    //sampling has now been officially concluded...need to clean up state
    int i;
    
#if 0
    atomic{
      gSamplingInProgress=FALSE;
      gGse=FALSE;
      gGseCal=FALSE;
    }
    
    cleanupTimers();
    for(i=0; i<MAX_SIMUL_CHANNELS; i++){
      gSampleInfo[i].sampleHeader.channelId = INVALID_CHANNEL_ID;
    } 
      
    //turn off the board...select channel 0
#endif
    return SUCCESS;
  }

  
  void postPrepareDone(uint32_t arg){
    uint8_t channelID = (uint32_t)arg;
    //TODO:  do some checking here based on the arguments
    signal GenericSampling.prepareDone(channelID,SUCCESS);
  }

  void postPrepareDoneFail(uint32_t arg){
    uint8_t channelID = (uint32_t)arg;
    //TODO:  do some checking here based on the arguments
    signal GenericSampling.prepareDone(channelID,FAIL);
  }
  

  /**
   * Prepare to peform sampling. 
   * @param channel The sensor channel id
   * @param samplingRate The sampling rate specified in Hz
   * @param numSamples The number of samples to collect
   * @param sampleWidth The number of bits per sample 
   * @param streaming TRUE for streaming (sampling will only
   *   end when stop is called.
   * @param warmup The sensor warmup time in microseconds, this will imply
   *   that once the start function is called, the sensor will turn on and 
   *   the samples will be dropped for at least warmup microseconds
   * @param type The sensor type to be sampled.  Some boards might expose 
   *   multiple type sensors on one channel.  The value is an enum that is 
   *   sensor board specific
   * @param function The sensor driver can support some form of post 
   *   processing capability (e.g. average, FFT, etc).  This supported values
   *   in this field will be sensor board specfic. Note that the meaning 
   *   of the numSamples parameter will be dependent on the post processing 
   *   function.
   * @param other this is an array of type value pairs that will capture
   *   board specific parameters that don't need to be applied to all boards
   *   The last item in the array will have a type 0 to indidate end of list
   * @return If the result is SUCCESS, <code>ready</code> will be signaled
   *   If the result is FAIL, no sampling will happen.
   */  

  command result_t GenericSampling.prepare(uint8_t channel, 
					     uint32_t samplingRate, 
					     uint32_t numSamples, 
					     uint8_t sampleWidth, 
					     bool streaming, 
					     uint32_t warmup, 
					     uint32_t type, 
					     uint32_t function, 
					     TypeValItem *other){
    
    /***************
cases that need to be watched out for:
    
1.) preparing the same channel multiple times....error or override?
2.) We currently allow at most 2 simul channels of which 1 can be a data channel and 1 can be a tach
3.) Must check that we have at most 1 data channel
4.) Must check that we have at most 1 tach channel

    *************/
    if(channel > LAST_CHANNEL){
      trace(DBG_USR1,"FAIL:  GenericSampling.prepare called with invalid channelId\r\n");
      return FAIL;
    }
    
    if(call ChannelManager.prepareChannel(channel, 
					  samplingRate, 
					  numSamples, 
					  sampleWidth,
					  streaming, 
					  warmup, 
					  type, 
					  function, 
					  other) == SUCCESS){
      
      POST_PARAMTASK(postPrepareDone,channel);
      return SUCCESS;
    }
    else{
      return FAIL;
    }
  }
  
  
  /**
   * Prepare a trigger channel
   * @param channel The sensor channel id
   * @param samplingRate The sampling rate specified in Hz
   * @param numSamples The number of samples to collect
   * @param sampleWidth The number of bits per sample 
   * @param streaming TRUE for streaming (sampling will only
   *   end when stop is called.
   * @param warmup The sensor warmup time in microseconds, this will imply
   *   that once the start function is called, the sensor will turn on and 
   *   the samples will be dropped for at least warmup microseconds
   * @param type The sensor type to be sampled.  Some boards might expose 
   *   multiple type sensors on one channel.  The value is an enum that is 
   *   sensor board specific
   * @param function The sensor driver can support some form of post 
   *   processing capability (e.g. average, FFT, etc).  This supported values
   *   in this field will be sensor board specfic. Note that the meaning 
   *   of the numSamples parameter will be dependent on the post processing 
   *   function.
   * @param other this is an array of type value pairs that will capture
   *   board specific parameters that don't need to be applied to all boards
   *   The last item in the array will have a type 0 to indidate end of list
   * @param storeData if TRUE the trigger channel is sampled like a regular
   *   channel and the data is stored in the same way.  If FALSE, the trigger
   *   channel data is just used for the purpose of triggering another channel
   * @return If the result is SUCCESS, <code>ready</code> will be signaled
   *   If the result is FAIL, no sampling will happen.
   */
  command result_t GenericSampling.prepareTrigger(uint8_t channel, 
						  uint32_t samplingRate, 
						  uint32_t numSamples, 
						  uint8_t sampleWidth, 
						  bool streaming, 
						  uint32_t warmup, 
						  uint32_t type, 
						  uint32_t function, 
						  TypeValItem *other, 
						  bool storeData){
    
    trace(DBG_USR1,"ERROR:  GenericSampling.prepareTrigger called.  This should not happen!\r\n");
    return FAIL;
  }


  /**
   * Report if sampling can be started
   * @param channel The sensor channel id
   * @param ok SUCCESS if sampling can be started by calling 
   *   <code>start</code>, FAIL otherwise
   * @return Ignored
   */
  default event result_t GenericSampling.prepareDone(uint8_t channel, result_t ok){
    return SUCCESS;
  }
     
  /** 
   * Start sampling requested by previous <code>prepare</code>
   *   If multiple channels are being passed in a list, then the sensor
   *   board will start all the channel simultaneously if supported.  However
   *   if individual start calls are executed, these channels are assumed to
   *   be independent. 
   *   If a trigger is setup and linked to a target channel, when the target 
   *   channel is started, the trigger channel will be started instead and 
   *   the target channel will only be started if the trigger is invoked.
   * @param numChannels The number of channels listed in the channelList
   * @param channelList An array of channel id values to be started
   * @param timeout if the complete collection is not done within timeout
   *   msec, the board will stop the capture and signal the samplingDone
   *   with a timeout error condition
   * @return SUCCESS if sampling started (<code>done</code> will be signaled
   *   when it complates), FAIL if it didn't.
   */
  command result_t GenericSampling.start(uint8_t numChannels, 
					 uint8_t *channelList, 
					 uint32_t timeout){
    
    //need to figure out whether we have info about the channels that are being requested
    //gSampleHeaders contains the information about the channels that we're currently aware of
    //
    
    //start channels will actuall start the channels and do some error checking.
    //in this module's model, channels will get started, warmed up, and then tested for trigger
    //conditions before getting written

#if 1    
    struct mallinfo minfo = mallinfo();
    
    trace(DBG_USR1,"Total space allocated from system = \t%10u\r\n",minfo.arena);
    trace(DBG_USR1,"Number of non-inuse chunks = \t\t%10u\r\n", minfo.ordblks);
    trace(DBG_USR1,"Number of MMAPPED regions = \t\t%10u\r\n", minfo.hblks);
    trace(DBG_USR1,"Total space in MMAPPED regions = \t%10u\r\n", minfo.hblkhd);
    trace(DBG_USR1,"Total allocated space = \t\t%10u\r\n", minfo.uordblks);
    trace(DBG_USR1,"Total non-inuse space = \t\t%10u\r\n", minfo.fordblks);
    trace(DBG_USR1,"top-most, releasable space = \t\t%10u\r\n", minfo.keepcost);
#endif   
    
    printList("GenericSampling.start() called with channel #'s: ", numChannels, channelList);
    
    if(call ChannelManager.startChannels(numChannels, channelList) == FAIL){
      return FAIL;
    }
    
    //start the overall acquisition timeout timer
    if(timeout){
      call AcquisitionTimeout.start(TIMER_ONE_SHOT,timeout);
    }
    
    return SUCCESS;
  }

  event result_t ChannelManager.startChannelsDone(uint8_t numChannels, uint8_t *channelList){
    call ChannelManager.warmupChannels(numChannels, channelList);
    return SUCCESS;
  }
  
  #define MAX_TRIGGER_TIMEOUT (1000)

  event result_t ChannelManager.warmupChannelsDone(uint8_t numChannels, 
						   uint8_t *channelList){
    
    trace(DBG_USR1,"Channel warmup completed\r\n");
    call ChannelManager.waitForData(numChannels, channelList);
    return SUCCESS;
  }
  
  /** 
   * Stop sampling started by earlier <code>start</code>
   * @param numChannels The number of channels listed in the channelList
   * @param channelList An array of channel id values to be started
   * @return SUCCESS if sampling can be stopped (<code>done</code> will 
   *   be signaled shortly), FAIL if it can't.
   */
  command result_t GenericSampling.stop(uint8_t numChannels, 
					uint8_t *channelList){

    printList("GenericSampling.stop() called with channel #'s: ", numChannels, channelList);
    
    return call ChannelManager.stopChannels(numChannels, channelList);
  }

  /**
   * Report sampling completion
   * @param channel The sensor channel id
   * @param status SUCCESS if sampling was succesful, FAIL if it failed. Failure
   *   may be due to the sampling interval being too short or to a data
   *   logging poblem.
   * @param numSamples Number of samples of data collected
   * @return Ignored
   */
  default event result_t GenericSampling.samplingDone(uint8_t channel, 
						      result_t status, 
						      uint32_t numSamples){

    return SUCCESS;
  }

  /**
   * This function supports triggering channel sampling from one or many
   *   channels based on the behavior of a trigger channel.
   * 
   * @param boolOp Boolean operation to combine different triggers.  
   *   Supported enum is board specific
   * @param triggerFunction The supported functions are board specific
   *   examples are rising edge, falling edge, max, min, average
   * @param triggerValue The tigger function evaluates the function and 
   *   compares to the value to evaulate the trigger
   * @param triggerChannel the channel id of the trigger
   * @param targetChannel the channel id of the triggered channel 
   * 
   * @return SUCCESS indicates the trigger was setup
   **/
    

  command result_t GenericSampling.AddTrigger(uint8_t boolOp, 
					      uint32_t triggerFunction,
					      float triggerValue, 
					      uint32_t triggerWindowSamples,
					      uint8_t triggerChannel,
					      uint8_t targetChannel){

    return call ChannelManager.addTrigger(boolOp, 
					  triggerFunction, 
					  triggerValue, 
					  triggerWindowSamples,
					  triggerChannel, 
					  targetChannel);
  }

  /**
   * This function clears the preset trigger functionality
   * 
   * @param targetChannel the channel id of the target channel
   */
  command void GenericSampling.ClearTrigger(uint8_t targetChannel){
    
    return call ChannelManager.clearTrigger(targetChannel);
  }

  /**
   * Report that a target channel has been triggered (trigger invoked)
   * @param channel The target channel id 
   * @return Ignored
   */
  default event result_t GenericSampling.TargetChannelTriggered(uint8_t channel){
    return SUCCESS;
  }

  /**
   * Retrieve information about a supported board feature
   * @param feature supported list of features to be interogated is board
   *   specific.  This will be an enumerated list that is defined across
   *   sensor boards, and each sensor board will support a subset of the
   *   range.  There is a special feature (type 0), which will return the
   *   list of supported features by this board rather than the infromation
   *   about a specific feature.
   * @param options This is an array options relating to the passed feature
   *   The driver will allocate the array.  The caller shouldn't modify 
   *   the contents of the array, nor can it assume that the array will
   *   persist after the function returns.
   * @return The function returns the number of entries in the array
   *   0 means that the feature is not supported
   */
  command uint32_t GenericSampling.GetSupportedFeature(uint32_t feature, 
						       uint32_t *options){
    return 0;
  }

  /**
   * Returns the actual data width of the sample returned by the board
   *   given a desired sample width.  e.g. the caller can request 14 bit
   *   samples and the board can pack it into 16 bit samples. It also
   *   indicates the endianess of the samples
   * @param sampleWidth desired number of bits per sample
   * @param dataWidth driver will return the data width in bits used to
   *   pack these samples
   * @param littleEndian driver will return the endianess of the data.  
   *   FALSE for little endian, FALSE for big endian
   *   
   */ 

  command void GenericSampling.getSampleInfo(uint8_t sampleWidth, 
					     uint8_t *dataWidth, 
					     bool *littleEndian){

    return;
  }

  /**********************
WriteData interface
  *******************/
  

  event result_t ChannelManager.DataReady(uint8_t channel, uint16_t numSamples, bool done){
    if(done){
      cleanupTimers();
      return signal GenericSampling.samplingDone(channel, SUCCESS, numSamples); 
    }
    return SUCCESS;
  }
}

Index: BoardManager.nc
===================================================================
RCS file: /cvsroot/tinyos/tinyos-1.x/contrib/imote2/tos/sensorboards/Framework/BoardManager.nc,v
retrieving revision 1.1
retrieving revision 1.2
diff -C2 -d -r1.1 -r1.2
*** BoardManager.nc	25 Oct 2006 15:03:51 -0000	1.1
--- BoardManager.nc	5 Mar 2007 07:29:19 -0000	1.2
***************
*** 11,14 ****
--- 11,16 ----
    command result_t enableChannelsToBeSampled(uint8_t numChannels, uint8_t *channelList);
    
+   event result_t enableChannelsToBeSampledDone(uint8_t numChannels, uint8_t *channelList);
+  
    //operates on a list of dataChannels
    command result_t startDataChannels(uint8_t numChannels, uint8_t *channelList);

Index: ChannelManager.nc
===================================================================
RCS file: /cvsroot/tinyos/tinyos-1.x/contrib/imote2/tos/sensorboards/Framework/ChannelManager.nc,v
retrieving revision 1.1
retrieving revision 1.2
diff -C2 -d -r1.1 -r1.2
*** ChannelManager.nc	25 Oct 2006 15:03:52 -0000	1.1
--- ChannelManager.nc	5 Mar 2007 07:29:19 -0000	1.2
***************
*** 15,18 ****
--- 15,40 ----
    
    command result_t startChannels(uint8_t numChannels, 
+ 				 uint8_t *channelList);
+ 
+   
+   /**
+    *
+    *event that indicates that the channels have successfully been started and that it is ok
+    *to start warming them up
+    *
+    *
+    **/
+   
+   event result_t startChannelsDone(uint8_t numChannels, 
+ 				   uint8_t *channelList);
+   /**
+    *command to "stop" a list of channels.  In the context of the channel manager, the
+    *stop function is used to actually stop the sampling process on group of channels
+    *
+    *
+    *
+    **/
+   
+   command result_t stopChannels(uint8_t numChannels, 
  			 uint8_t *channelList);
    

Index: ChannelManagerM.nc
===================================================================
RCS file: /cvsroot/tinyos/tinyos-1.x/contrib/imote2/tos/sensorboards/Framework/ChannelManagerM.nc,v
retrieving revision 1.1
retrieving revision 1.2
diff -C2 -d -r1.1 -r1.2
*** ChannelManagerM.nc	25 Oct 2006 15:03:52 -0000	1.1
--- ChannelManagerM.nc	5 Mar 2007 07:29:19 -0000	1.2
***************
*** 19,22 ****
--- 19,26 ----
      interface WriteData;
      interface WallClock;
+ #ifdef USE_UNIQUE_SEQUENCE_ID
+     interface UniqueSequenceID;
+     interface StdControl as UniqueSequenceIDControl;
+ #endif  
    }
  }
***************
*** 25,28 ****
--- 29,33 ----
  #include "frameworkconfig.h"
  #include "sensorboard.h"
+ #include "paramtask.h"
    
  #define WRAPPERHEADER_FIRSTOFFSET (12)
***************
*** 48,55 ****
    bool channelInProgress[TOTAL_DATA_CHANNELS];
    uint8_t gDataChannelPreparedChannel[TOTAL_DATA_CHANNELS];
!   queue_t warmupTimeQueue;
!   
    uint32_t gSequenceID;
  
    command result_t StdControl.init(){
      int i;
--- 53,67 ----
    bool channelInProgress[TOTAL_DATA_CHANNELS];
    uint8_t gDataChannelPreparedChannel[TOTAL_DATA_CHANNELS];
!   ptrqueue_t warmupTimeQueue;
!   //we store a redundant copy of the sensor type in order to help keep the line between dependent and independent 
!   //sampleHeader representations
!   uint32_t gSensorTypes[TOTAL_DATA_CHANNELS];
! 
    uint32_t gSequenceID;
  
+   void signalDataReady(uint32_t arg);
+   DEFINE_PARAMTASK(signalDataReady); 
+   
+   
    command result_t StdControl.init(){
      int i;
***************
*** 61,71 ****
      }
      
!     initqueue(&warmupTimeQueue, defaultQueueSize);
!     gSequenceID = 0; //initialize just to make sure
      return SUCCESS;
    }
    
    command result_t StdControl.start(){
!     
      return SUCCESS;
    }
--- 73,93 ----
      }
      
!     initptrqueue(&warmupTimeQueue, defaultQueueSize);
! #ifdef USE_UNIQUE_SEQUENCE_ID
!     call UniqueSequenceIDControl.init();
! #endif
      return SUCCESS;
    }
    
    command result_t StdControl.start(){
! #ifdef USE_UNIQUE_SEQUENCE_ID
!     call UniqueSequenceIDControl.start();
!     if( (gSequenceID = call UniqueSequenceID.GetNextSequenceID()) == 0){
!       trace(DBG_USR1,"ERROR:  UniqueSequenceID.GetNextSequenceID returned 0...sequences number is most likely not unique!!!\r\n");
!     }
! #else    
!     gSequenceID = 0; //initialize just to make sure
! #endif
! 
      return SUCCESS;
    }
***************
*** 98,102 ****
    result_t isSupportedFunction(uint8_t channel, uint32_t function);
  
! 
    command result_t ChannelManager.startChannels(uint8_t numChannels, 
  					uint8_t *channelList){
--- 120,164 ----
    result_t isSupportedFunction(uint8_t channel, uint32_t function);
  
!   command result_t ChannelManager.stopChannels(uint8_t numChannels, 
! 						uint8_t *channelList){
!     
!     uint32_t i;
!     uint8_t *translatedChannelList;
!     
!     if(channelList == NULL){
!       trace(DBG_USR1,"ChannelManager.stopChannels passed NULL channelList\r\n");
!       return FAIL;
!     }
!     
!     //check to make sure that all of the channels listed are a part of the same simultaneous sampling group
!     //if our board's capabilities table is configured correctly and this function is used correctly, the
!     //simulChannelGroup for all of the channels in our list should be the same
!     for(i=1; i<numChannels; i++){
!       if(dataChannelCapabilitiesTable[channelList[0]].simulChannelGroup != dataChannelCapabilitiesTable[channelList[i]].simulChannelGroup){
! 	trace(DBG_USR1,"FAIL:  GenericSampling.start requires that all started channels be a member of the same simultaneous sampling group\r\n");
! 	return FAIL;
!       }
!     }
!     //all of the channels are part of the same simultaneous sampling group.
!     
!       //translate this list of channels to a list of data channels for the triggermanager!!!
!     
!     if((translatedChannelList = malloc(numChannels*sizeof(*translatedChannelList))) == NULL){
!       trace(DBG_USR1,"ChannelManager.waitForData unable to allocate translated channel array\r\n");
!       return FAIL;
!     }
!     MALLOC_DBG(__FILE__,"stopChannels",translatedChannelList,numChannels*sizeof(*translatedChannelList));
!     
!     for(i=0; i<numChannels; i++){
!       getDataChannelFromChannel(channelList[i], &(translatedChannelList[i]));
!     }
!     
!     call TriggerManager.cancelWaitForTrigger(numChannels, translatedChannelList);
!       
!     FREE_DBG(__FILE__,"stopChannel",translatedChannelList);
!     free(translatedChannelList);
!     return SUCCESS;
!   }
!   
    command result_t ChannelManager.startChannels(uint8_t numChannels, 
  					uint8_t *channelList){
***************
*** 104,108 ****
      
      uint32_t i,j;
!     
      if(numChannels == 0){
        //this is an error
--- 166,173 ----
      
      uint32_t i,j;
! #ifdef USE_UNIQUE_SEQUENCE_ID
!     uint32_t nextUID;
! #endif
! 
      if(numChannels == 0){
        //this is an error
***************
*** 133,136 ****
--- 198,207 ----
  	return FAIL;
        }
+       //now that we have the dataChannel, we need to set the warmup info for this datachannel
+       if(call TriggerManager.setWarmupInfo(dataChannel,gSensorTypes[dataChannel]) == FAIL){
+ 	trace(DBG_USR1,"FAIL:  GenericSampling.start unable to set Warmup Info for dataChannel %d\r\n",dataChannel);
+ 	return FAIL;
+       }
+       
        if(gDataChannelPreparedChannel[dataChannel] != channelList[i]){
  	//this channel was not actually prepared
***************
*** 148,151 ****
--- 219,224 ----
      
      //turn on the channels that we need to turn on...
+     //this function operates on the original channel list instead of a translated list because the boardmanager
+     //has intimate knowledge of the board and its channel mapping anyway
      if(call BoardManager.enableChannelsToBeSampled(numChannels, channelList) == FAIL){
        trace(DBG_USR1,"FAIL:  GenericSamplng.start unable to enable channel list to be sampled\r\n");
***************
*** 153,180 ****
      }
  
      gSequenceID++;
!     
      return SUCCESS;
    }
    
    task void warmupTimerExpiredTask(){
      
      channelList_t *list;
  
      //get the entry at the top of queue
!     if(popqueue(&warmupTimeQueue,(uint32_t *)&list)){
!       //found something in the queue
!     }
!     else{
!       trace(DBG_USR1,"FATAL ERROR...warmupTimerExpiredTask did not find a queue entry\r\n");
!       return;
      }
!     
      signal ChannelManager.warmupChannelsDone(list->numChannels, list->channelList);
      
      free(list->channelList);
      free(list);
      
!     if(peekqueue(&warmupTimeQueue,(uint32_t *)&list)){
        trace(DBG_USR1,"Info:  warmupTimerExpiredTask found a concurrent warmup request\r\n");
        call ADCWarmupTimer.start(TIMER_ONE_SHOT,list->warmup/1000);
--- 226,269 ----
      }
  
+ #ifdef USE_UNIQUE_SEQUENCE_ID
+     if( (nextUID = call UniqueSequenceID.GetNextSequenceID()) == 0){
+       trace(DBG_USR1,"ERROR:  UniqueSequenceID.GetNextSequenceID returned 0...sequences number is not unique!!!\r\n");
+       gSequenceID++;
+     }
+     else{
+       gSequenceID = nextUID;
+     }
+ #else    
      gSequenceID++;
! #endif
! 
      return SUCCESS;
    }
    
+   event result_t BoardManager.enableChannelsToBeSampledDone(uint8_t numChannels,uint8_t *channelList){
+     return signal ChannelManager.startChannelsDone(numChannels, channelList);
+   }
+   
    task void warmupTimerExpiredTask(){
      
      channelList_t *list;
+     int status;
  
      //get the entry at the top of queue
!     list = popptrqueue(&warmupTimeQueue,&status);
!     if(status == 0){
!       printFatalErrorMsg("ChannelManager:  Missing channelList in warmupTimerExpiredTask\r\n",0);
      }
!         
      signal ChannelManager.warmupChannelsDone(list->numChannels, list->channelList);
      
+     
+     FREE_DBG(__FILE__,"warmupTimerExpiredTask",list->channelList);
      free(list->channelList);
+     FREE_DBG(__FILE__,"warmupTimerExpiredTask",list);
      free(list);
      
!     list = peekptrqueue(&warmupTimeQueue,&status);
!     if(status == 1){
        trace(DBG_USR1,"Info:  warmupTimerExpiredTask found a concurrent warmup request\r\n");
        call ADCWarmupTimer.start(TIMER_ONE_SHOT,list->warmup/1000);
***************
*** 231,251 ****
      
      
!     if((newList = malloc(sizeof(channelList_t)))==NULL){
!       trace(DBG_USR1,"FATAL ERROR:  unable to allocate enough memory in warmupChannels\r\n");
!       return FAIL;
!     }
!     
      //got enough memory, now allocate the internal array so that we can copy state
      if( (newList->channelList = malloc(numChannels)) == NULL){
        //we didn't get the memory we need...deallocate and FAIL
        free(newList);
        trace(DBG_USR1,"FATAL ERROR:  unable to allocate enough memory in warmupChannels\r\n");
        return FAIL;
      }
      //got our memory
!     newList->warmup = time;
      memcpy(newList->channelList,channelList,numChannels);
      newList->numChannels = numChannels;
!     pushqueue(&warmupTimeQueue,(uint32_t)newList);
      
      if(totalTime > 0){
--- 320,340 ----
      
      
!     assert((newList = malloc(sizeof(channelList_t))));
!     MALLOC_DBG(__FILE__,"warmupChannels",newList,sizeof(channelList_t));
! 	   
      //got enough memory, now allocate the internal array so that we can copy state
      if( (newList->channelList = malloc(numChannels)) == NULL){
        //we didn't get the memory we need...deallocate and FAIL
        free(newList);
+       FREE_DBG(__FILE__,"warmupChannels",newList);
        trace(DBG_USR1,"FATAL ERROR:  unable to allocate enough memory in warmupChannels\r\n");
        return FAIL;
      }
+     MALLOC_DBG(__FILE__,"warmupChannels",newList->channelList,numChannels);
      //got our memory
!     newList->warmup = totalTime;
      memcpy(newList->channelList,channelList,numChannels);
      newList->numChannels = numChannels;
!     pushptrqueue(&warmupTimeQueue,newList);
      
      if(totalTime > 0){
***************
*** 326,329 ****
--- 415,423 ----
        return FAIL;
      }
+     //make sure that this is a legit channel before we start using it
+     assert(dataChannel < TOTAL_DATA_CHANNELS);
+     
+     //store the sensor type locally so that we can more easily retrieve it later
+     gSensorTypes[dataChannel] = type;
      
      pSi = &gSampleInfo[dataChannel];
***************
*** 633,645 ****
  					      uint16_t numBytesTotal, 
  					      uint16_t numSamples,
! 					      uint64_t timestamp,
! 					      bool done){
!     
!     
!     uint8_t channel;
!     sampleInfo_t *pSi;
!     
      
      call ChannelParamsManager.setNumSamples[dataChannel](numSamples);
      call ChannelParamsManager.setMicroTimestamp[dataChannel](timestamp);
      call ChannelParamsManager.setWallTimestamp[dataChannel](call WallClock.getWallClock());
--- 727,739 ----
  					      uint16_t numBytesTotal, 
  					      uint16_t numSamples,
! 					      uint64_t timestamp){
      
+         
      call ChannelParamsManager.setNumSamples[dataChannel](numSamples);
+     if( ((timestamp >> 32) & 0xFFFFFFFF) == 0xFFFFFFFF){
+       //if upper 32 bits of the timetamps are all 1's, print an error
+       trace(DBG_USR1,"ERROR:  Upper 32 bits of microsecond timestamp are all 1's\r\n");
+     }
+        
      call ChannelParamsManager.setMicroTimestamp[dataChannel](timestamp);
      call ChannelParamsManager.setWallTimestamp[dataChannel](call WallClock.getWallClock());
***************
*** 651,668 ****
      call ChannelParamsManager.incrementSampleOffset[dataChannel](numSamples);
          
-     getChannelFromDataChannel(dataChannel,&channel);
-     pSi = &gSampleInfo[dataChannel];
-     
      call WriteData.write(0, 
  			 buffer, 
  			 numBytesWrite);
!         
!     if(done){
!       signal ChannelManager.DataReady(channel, pSi->numSamples, done);
!     }
      
      return SUCCESS;
    }
  
    command result_t ChannelManager.waitForData(uint8_t numChannels, uint8_t *targetChannels){
      //translate this list of channels to a list of data channels for the triggermanager!!!
--- 745,775 ----
      call ChannelParamsManager.incrementSampleOffset[dataChannel](numSamples);
          
      call WriteData.write(0, 
  			 buffer, 
  			 numBytesWrite);
!       
!     return SUCCESS;
!   }
!   
!   event result_t TriggerManager.CollectionDone(uint8_t dataChannel){
      
+     POST_PARAMTASK(signalDataReady, dataChannel);
      return SUCCESS;
    }
+   
+   void signalDataReady(uint32_t dataChannel){
+     
+     uint8_t channel;
+     sampleInfo_t *pSi = &gSampleInfo[dataChannel];
+     
+     getChannelFromDataChannel(dataChannel,&channel);
+     
+     signal ChannelManager.DataReady(channel, pSi->numSamples, TRUE);
+     
+     return;
+     
+   }
  
+   
    command result_t ChannelManager.waitForData(uint8_t numChannels, uint8_t *targetChannels){
      //translate this list of channels to a list of data channels for the triggermanager!!!
***************
*** 678,681 ****
--- 785,789 ----
        return FAIL;
      }
+     MALLOC_DBG(__FILE__,"waitForData",translatedChannelList,numChannels*sizeof(*translatedChannelList));
      
      for(i=0; i<numChannels; i++){
***************
*** 713,716 ****
--- 821,825 ----
      }    
      
+     FREE_DBG(__FILE__,"waitForData",translatedChannelList);
      free(translatedChannelList);
      return SUCCESS;

Index: ChannelParamsManagerM.nc
===================================================================
RCS file: /cvsroot/tinyos/tinyos-1.x/contrib/imote2/tos/sensorboards/Framework/ChannelParamsManagerM.nc,v
retrieving revision 1.1
retrieving revision 1.2
diff -C2 -d -r1.1 -r1.2
*** ChannelParamsManagerM.nc	25 Oct 2006 15:03:52 -0000	1.1
--- ChannelParamsManagerM.nc	5 Mar 2007 07:29:19 -0000	1.2
***************
*** 267,271 ****
    command result_t ChannelParamsManager.setWallTimestamp[uint8_t instance](uint32_t timeStamp){
      
!     gSampleHeaders[instance].wallClockTimeStamp = timeStamp;
      return SUCCESS;
    }
--- 267,273 ----
    command result_t ChannelParamsManager.setWallTimestamp[uint8_t instance](uint32_t timeStamp){
      
!     if(gSampleHeaders[instance].sampleOffset == 0){
!       gSampleHeaders[instance].wallClockTimeStamp = timeStamp;
!     }
      return SUCCESS;
    }

Index: SensorData.nc
===================================================================
RCS file: /cvsroot/tinyos/tinyos-1.x/contrib/imote2/tos/sensorboards/Framework/SensorData.nc,v
retrieving revision 1.1
retrieving revision 1.2
diff -C2 -d -r1.1 -r1.2
*** SensorData.nc	25 Oct 2006 15:03:52 -0000	1.1
--- SensorData.nc	5 Mar 2007 07:29:19 -0000	1.2
***************
*** 68,70 ****
--- 68,80 ----
  
    event uint8_t *getSensorDataDone(uint8_t *buffer, uint32_t numSamples, uint64_t timestamp, float ADCScale, float ADCOffset);
+ 
+   /**
+    * event that gets signalled once the actual process of sampling has completely stopped.  This event will be signaled
+    * sometime after getSensorDataDone has a null returned to it
+    *
+    *
+    *
+    **/
+   
+   event result_t getSensorDataStopped();
  }

Index: TriggerManager.nc
===================================================================
RCS file: /cvsroot/tinyos/tinyos-1.x/contrib/imote2/tos/sensorboards/Framework/TriggerManager.nc,v
retrieving revision 1.1
retrieving revision 1.2
diff -C2 -d -r1.1 -r1.2
*** TriggerManager.nc	25 Oct 2006 15:03:53 -0000	1.1
--- TriggerManager.nc	5 Mar 2007 07:29:19 -0000	1.2
***************
*** 40,43 ****
--- 40,56 ----
  				     uint16_t headerSize, 
  				     uint16_t footerSize);
+ 
+   /**
+    * set the collection specification need for channel warmup.
+    * 
+    * @param channel: that this specification applies to.  Channel may either be a target channel 
+    *                or a trigger channel
+    * @param type:  the type of sensor to be warmed up.  Used in the case of multiple different possible sensor types.
+    * 
+    * @return FAIL if this is not possible; SUCCESS otherwise
+    *
+    **/
+   command result_t setWarmupInfo(uint8_t channel, 
+ 				 uint32_t type);
    
    /**
***************
*** 90,95 ****
  			       uint16_t numBytesTotal, 
  			       uint16_t numSamples,
! 			       uint64_t timestamp,
! 			       bool done);
!   
  }
--- 103,108 ----
  			       uint16_t numBytesTotal, 
  			       uint16_t numSamples,
! 			       uint64_t timestamp);
! 			       
!   event result_t CollectionDone(uint8_t dataChannel);
  }

Index: TriggerManagerM.nc
===================================================================
RCS file: /cvsroot/tinyos/tinyos-1.x/contrib/imote2/tos/sensorboards/Framework/TriggerManagerM.nc,v
retrieving revision 1.1
retrieving revision 1.2
diff -C2 -d -r1.1 -r1.2
*** TriggerManagerM.nc	25 Oct 2006 15:03:53 -0000	1.1
--- TriggerManagerM.nc	5 Mar 2007 07:29:19 -0000	1.2
***************
*** 32,35 ****
--- 32,36 ----
      uint8_t triggerChannel;
      uint8_t boolOp;
+     bool bInitialized;  //this field is for future support for optimizing trigger computation
    }triggerInfo_t;
  
***************
*** 50,53 ****
--- 51,55 ----
      uint8_t  sampleWidth;
[...1275 lines suppressed...]
+       return FAIL;
+     }
+     
+     if(call SensorData.setSensorType[channel](type) == FAIL){
+       trace(DBG_USR1,"FATAL ERROR:  SensorData.setSensorType failed for channel %d\r\n",channel);
+       return FAIL;
+     }
+     return SUCCESS;
+   } 
+   
    command result_t TriggerManager.setCollectionInfo(uint8_t channel, 
  						    uint32_t samplingRate, 
***************
*** 1433,1436 ****
--- 1728,1732 ----
      pCI->footerSize = footerSize;
      pCI->bDone = FALSE;
+     pCI->bStopped = FALSE;
  #ifdef DOPRETRIGGER
      pCI->numBuffersNeeded = 1;

Index: sensorTypes.h
===================================================================
RCS file: /cvsroot/tinyos/tinyos-1.x/contrib/imote2/tos/sensorboards/Framework/sensorTypes.h,v
retrieving revision 1.1
retrieving revision 1.2
diff -C2 -d -r1.1 -r1.2
*** sensorTypes.h	25 Oct 2006 15:03:53 -0000	1.1
--- sensorTypes.h	5 Mar 2007 07:29:19 -0000	1.2
***************
*** 58,62 ****
    SENSOR_ANALOG_RANGE_PLUSMINUS5V = 2,
    SENSOR_ANALOG_RANGE_PLUS10V = 3,
!   SENSOR_ANALOG_RANGE_PLUSMINUS10V = 4
  };  
    
--- 58,64 ----
    SENSOR_ANALOG_RANGE_PLUSMINUS5V = 2,
    SENSOR_ANALOG_RANGE_PLUS10V = 3,
!   SENSOR_ANALOG_RANGE_PLUSMINUS10V = 4,
!   SENSOR_ANALOG_RANGE_PLUSMINUS2P5V = 5
!   
  };  
    



More information about the Tinyos-contrib-commits mailing list