示例#1
0
/**
 * Read part of a 512 byte block from a SD card.
 *  
 * \param[in] block Logical block to be read.
 * \param[in] offset Number of bytes to skip at start of block
 * \param[out] dst Pointer to the location that will receive the data. 
 * \param[in] count Number of bytes to read
 * \return The value one, true, is returned for success and
 * the value zero, false, is returned for failure.
 */
uint8_t sdReadData(uint32_t block,
      uint16_t offset, uint8_t *dst, uint16_t count) {
   uint16_t i;

   if (count == 0) return 1;
   if ((count + offset) > 512) {
      return 0;
   }
   if (!inBlock_ || block != block_ || offset < offset_) {
      block_ = block;

      // use address if not SDHC card
      if (sdType()!= SD_CARD_TYPE_SDHC) block <<= 9;
      if (sdCardCommand(CMD17, block)) {
         error1(SD_CARD_ERROR_CMD17);
         return 0;
      }
      if (!sdWaitStartBlock()) {
         return 0;
      }
      offset_ = 0;
      inBlock_ = 1;
   }

   // start first SPI transfer
   SPDR = 0XFF;

   // skip data before offset
   for (;offset_ < offset; offset_++) {
      while(!(SPSR & (1 << SPIF)));
      SPDR = 0XFF;
   }

   // transfer data
   uint16_t n = count - 1;
   for (i = 0; i < n; i++) {
      while(!(SPSR & (1 << SPIF)));
      dst[i] = SPDR;
      SPDR = 0XFF;
   }

   // wait for last byte
   while(!(SPSR & (1 << SPIF)));
   dst[n] = SPDR;
   offset_ += count;
   if (!partialBlockRead_ || offset_ >= 512) sdReadEnd();
   return 1;
}
示例#2
0
/**
  Simple cone using dimensions to be used to define cone composed of 1 single material
  @author Clement Helsens
**/
static DD4hep::Geometry::Ref_t
createSimpleCone(DD4hep::Geometry::LCDD& lcdd, xml_h e, DD4hep::Geometry::SensitiveDetector sensDet) {
  xml_det_t x_det = e;
  std::string name = x_det.nameStr();
  DD4hep::Geometry::DetElement coneDet(name, x_det.id());

  DD4hep::Geometry::Volume experimentalHall = lcdd.pickMotherVolume(coneDet);

  xml_comp_t coneDim(x_det.child(_U(dimensions)));
  DD4hep::Geometry::Cone cone(coneDim.dz(), coneDim.rmin1(), coneDim.rmax1(), coneDim.rmin2(), coneDim.rmax2());

  DD4hep::Geometry::Volume coneVol(x_det.nameStr() + "_SimpleCone", cone, lcdd.material(coneDim.materialStr()));

  if (x_det.isSensitive()) {
    DD4hep::XML::Dimension sdType(x_det.child(_U(sensitive)));
    coneVol.setSensitiveDetector(sensDet);
    sensDet.setType(sdType.typeStr());  
  }

  DD4hep::Geometry::PlacedVolume conePhys;

  double zoff = coneDim.z_offset();
  if (fabs(zoff) > 0.000000000001) {
    double reflectionAngle = 0.;
    if (coneDim.hasAttr(_Unicode(reflect))) {
      if (coneDim.reflect()) {
        reflectionAngle = M_PI;
        }
    }
    DD4hep::Geometry::Position trans(0., 0., zoff);
    conePhys =
        experimentalHall.placeVolume(coneVol, DD4hep::Geometry::Transform3D(DD4hep::Geometry::RotationX(reflectionAngle), trans));
  } else
    conePhys = experimentalHall.placeVolume(coneVol);

  conePhys.addPhysVolID("system", x_det.id());

  coneDet.setPlacement(conePhys);

  coneDet.setVisAttributes(lcdd, x_det.visStr(), coneVol);
  return coneDet;
}
示例#3
0
/**
 * Initialize a SD flash memory card.
 *
 * \param[in] slow If \a slow is false (zero) the SPI bus will
 * be initialize at a speed of 8 Mhz.  If \a slow is true (nonzero)
 * the SPI bus will be initialize a speed of 4 Mhz. This may be helpful
 * for some SD cards with Version 1.0 of the Adafruit Wave Shield.
 *
 * \return The value one, true, is returned for success and
 * the value zero, false, is returned for failure. 
 *
 */  
uint8_t sdInit(uint8_t slow) {
   uint8_t r;
   uint16_t i;
   uint8_t retry;
   uint32_t t0=0;

   //pinMode(SS, OUTPUT);
   DDRB |= _BV(SS);

   //digitalWrite(SS, HIGH);
   PORTB |= _BV(SS);

   //pinMode(MOSI, OUTPUT);
   DDRB |= _BV(MOSI);

   //pinMode(MISO_PIN, INPUT);

   //pinMode(SCK, OUTPUT);
   DDRB |= _BV(SCK);

#if SPI_INIT_SLOW
   // Enable SPI, Master, clock rate f_osc/128
   SPCR = (1 << SPE) | (1 << MSTR) | (1 << SPR1) | (1 << SPR0);
#else  // SPI_INIT_SLOW
   // Enable SPI, Master, clock rate f_osc/64
   SPCR = (1 << SPE) | (1 << MSTR) | (1 << SPR1);
#endif  // SPI_INIT_SLOW

   // must supply min of 74 clock cycles with CS high.
   for (i = 0; i < 10; i++) spiSend(0XFF);

   // next two lines prevent re-init hang by cards that were in partial read
   spiSSLow();
   for (i = 0; i <= 512; i++) spiRec();

   // command to go idle in SPI mode
   for (retry = 0; ; retry++) {
      if ((r = sdCardCommand(CMD0, 0)) ==  R1_IDLE_STATE) break;
      if (retry == 10) {
         error2(SD_CARD_ERROR_CMD0, r);
         return 0;
      }
   }

   // check SD version
   r = sdCardCommand(CMD8, 0x1AA);
   if (r == R1_IDLE_STATE) {
      for(i = 0; i < 4; i++) {
         r = spiRec();
      }
      if (r != 0XAA) {
         error2(SD_CARD_ERROR_CMD8_ECHO, r);
         return 0;
      }
      sdSetType(SD_CARD_TYPE_SD2);
   }
   else if (r & R1_ILLEGAL_COMMAND) {
      sdSetType(SD_CARD_TYPE_SD1);
   }
   else {
      error2(SD_CARD_ERROR_CMD8, r);
   }

   // initialize card and send host supports SDHC if SD2
   t0=0;
   for (;;) {
      _delay_us(2);
      t0++;
      sdCardCommand(CMD55, 0);
      r = sdCardCommand(ACMD41, sdType() == SD_CARD_TYPE_SD2 ? 0X40000000 : 0);
      if (r == R1_READY_STATE) break;

      // timeout after 2 seconds
      if ((t0/1000) > 2000) {
         error1(SD_CARD_ERROR_ACMD41);
         return 0;
      }
   }

   // if SD2 read OCR register to check for SDHC card
   if (sdType() == SD_CARD_TYPE_SD2) {
      if(sdCardCommand(CMD58, 0)) {
         error1(SD_CARD_ERROR_CMD58);
         return 0;
      }
      if ((spiRec() & 0XC0) == 0XC0) sdSetType(SD_CARD_TYPE_SDHC);

      // discard rest of ocr
      for (i = 0; i < 3; i++) spiRec();
   }

   // use max SPI frequency unless slow is true
   SPCR &= ~((1 << SPR1) | (1 << SPR0)); // f_OSC/4

   if (!slow) SPSR |= (1 << SPI2X); // Doubled Clock Frequency: f_OSC/2
   spiSSHigh();
   return 1;
}