Exemplo n.º 1
0
void main ()
{
  vBSP430platformInitialize_ni();
  vBSP430uptimeStart_ni();
  vBSP430unittestInitialize();

  BSP430_CORE_DISABLE_INTERRUPT();
  /* Halt the timer without telling the infrastructure, since we
   * manage it explicitly.  Put the interrupts back on so that we can
   * synthesize overflow events and have them be handled normally. */
  hBSP430uptimeTimer()->hpl->ctl &= ~(MC0 | MC1);
  hBSP430uptimeTimer()->hpl->r = 0;
  hBSP430uptimeTimer()->overflow_count = 0;
  ulBSP430uptimeSetConversionFrequency_ni(32768);
  BSP430_CORE_ENABLE_INTERRUPT();

  testInitialConditions();
  testSetEpochFromTimeval();
  testEpochEra();
  testEpochValidate();
  testEpochAge();
  testNTPSequence();

  vBSP430unittestFinalize();
}
Exemplo n.º 2
0
void main ()
{
  hBSP430halSERIAL console = NULL;
  hBSP430halSERIAL uart = NULL;
  unsigned long prep_utt = 0;
  unsigned long emit_utt = 0;
  unsigned long done_utt = 0;

  vBSP430platformInitialize_ni();
  iBSP430consoleInitialize();

  console = hBSP430console();
  cprintf("\ntxcb " __DATE__ " " __TIME__ "\n");

  cprintf("\nConsole %p is on %s: %s\n", console,
          xBSP430serialName(BSP430_CONSOLE_SERIAL_PERIPH_HANDLE),
          xBSP430platformPeripheralHelp(BSP430_CONSOLE_SERIAL_PERIPH_HANDLE, 0));

  uart = hBSP430serialLookup(UART_PERIPH_HANDLE);
  if (NULL == uart) {
    cprintf("Failed to resolve secondary\n");
    return;
  }
  cprintf("\nSecondary %p is on %s: %s\n", uart,
          xBSP430serialName(UART_PERIPH_HANDLE),
          xBSP430platformPeripheralHelp(UART_PERIPH_HANDLE, 0));

  tx_buffer_.head = tx_buffer_.tail = 0;
  BSP430_HAL_ISR_CALLBACK_LINK_NI(sBSP430halISRVoidChainNode, uart->tx_cbchain_ni, tx_buffer_.cb_node, next_ni);
  uart = hBSP430serialOpenUART(uart, 0, 0, 9600);
  if (NULL == uart) {
    cprintf("Secondary open failed\n");
  }

  /* Need to enable interrupts so timer overflow events are properly
   * acknowledged */
  BSP430_CORE_ENABLE_INTERRUPT();
  while (1) {
    unsigned long next_prep_utt;
    char * obp;
    char * ob_end;

    next_prep_utt = ulBSP430uptime();
    obp = tx_buffer_.buffer;
    ob_end = obp + sizeof(tx_buffer_.buffer);
    obp += snprintf(obp, ob_end - obp, "prep %lu emit %lu\r\n", emit_utt - prep_utt, done_utt - emit_utt);
    ob_end = obp;
    BSP430_CORE_DISABLE_INTERRUPT();
    emit_utt = ulBSP430uptime_ni();
    prep_utt = next_prep_utt;
    tx_buffer_.tail = 0;
    tx_buffer_.head = obp - tx_buffer_.buffer;
    vBSP430serialWakeupTransmit_ni(uart);
    BSP430_CORE_LPM_ENTER_NI(LPM0_bits);
    /* Expect tail == head otherwise should not have awoken */
    done_utt = ulBSP430uptime();
  }
}
Exemplo n.º 3
0
void main ()
{
  hBSP430halPORT b0hal = hBSP430portLookup(BSP430_PLATFORM_BUTTON0_PORT_PERIPH_HANDLE);
  volatile sBSP430hplPORTIE * b0hpl;
  int b0pin = iBSP430portBitPosition(BSP430_PLATFORM_BUTTON0_PORT_BIT);

  vBSP430platformInitialize_ni();
  (void)iBSP430consoleInitialize();

  cprintf("\nbutton " __DATE__ " " __TIME__ "\n");

  cprintf("There's supposed to be a button at %s.%u\n",
          xBSP430portName(BSP430_PLATFORM_BUTTON0_PORT_PERIPH_HANDLE),
          b0pin);
  if (! b0hal) {
    cprintf("Whoops, guess it's not really there\n");
    return;
  }
  b0hpl = BSP430_PORT_HAL_GET_HPL_PORTIE(b0hal);
  button_state.button_cb.next_ni = b0hal->pin_cbchain_ni[b0pin];
  b0hal->pin_cbchain_ni[b0pin] = &button_state.button_cb;
  b0hpl->sel &= ~BSP430_PLATFORM_BUTTON0_PORT_BIT;
  b0hpl->dir &= ~BSP430_PLATFORM_BUTTON0_PORT_BIT;
#if (BSP430_PORT_SUPPORTS_REN - 0)
  BSP430_PORT_HAL_SET_REN(b0hal, BSP430_PLATFORM_BUTTON0_PORT_BIT, BSP430_PORT_REN_PULL_UP);
#endif /* BSP430_PORT_SUPPORTS_REN */
  if (b0hpl->in & BSP430_PLATFORM_BUTTON0_PORT_BIT) {
    button_state.in_mask = BSP430_PLATFORM_BUTTON0_PORT_BIT;
    b0hpl->ies |= BSP430_PLATFORM_BUTTON0_PORT_BIT;
  } else {
    button_state.in_mask = 0;
    b0hpl->ies &= ~BSP430_PLATFORM_BUTTON0_PORT_BIT;
  }
  b0hpl->ifg &= ~BSP430_PLATFORM_BUTTON0_PORT_BIT;
  b0hpl->ie |= BSP430_PLATFORM_BUTTON0_PORT_BIT;
  cprintf("Button is configured.  Try pressing it.  No debouncing is done.\n");
#if ! (configBSP430_CORE_LPM_EXIT_CLEAR_GIE - 0)
  cprintf("WARNING: Interrupts remain enabled after wakeup\n");
#endif /* configBSP430_CORE_LPM_EXIT_CLEAR_GIE */

  vBSP430ledSet(0, 1);

  while (1) {
    static const char * state_str[] = { "released", "pressed" };

    cprintf("Count %u, in mask 0x%02x: %s\n", button_state.count, button_state.in_mask, state_str[!button_state.in_mask]);

    /* Note that we've never turned interrupts on, but
     * BSP430_CORE_LPM_ENTER_NI() does so internally so the ISR can be
     * executed.  Whether they are cleared before returning to this
     * loop depends on #configBSP430_CORE_LPM_EXIT_CLEAR_GIE. */
    BSP430_CORE_LPM_ENTER_NI(LPM0_bits);
#if ! (configBSP430_CORE_LPM_EXIT_CLEAR_GIE - 0)
    /* Infrastructure didn't clear this, so we should */
    BSP430_CORE_DISABLE_INTERRUPT();
#endif /* configBSP430_CORE_LPM_EXIT_CLEAR_GIE */
  }
}
Exemplo n.º 4
0
void main ()
{
  sBSP430halPORT * hh10d_port = hBSP430portLookup(APP_HH10D_PORT_PERIPH_HANDLE);
  hBSP430halSERIAL i2c = hBSP430serialLookup(APP_HH10D_I2C_PERIPH_HANDLE);
  int uptime_Hz;
  int hh10d_offs;
  int hh10d_sens;

  vBSP430platformInitialize_ni();

  (void)iBSP430consoleInitialize();
  cprintf("\nApplication starting\n");
  BSP430_CORE_DELAY_CYCLES(10000);

  if (NULL == hh10d_port) {
    cprintf("\nERROR: No port HAL; did you enable configBSP430_HAL_%s?\n", xBSP430portName(APP_HH10D_PORT_PERIPH_HANDLE) ?: "whatever");
    return;
  }
Exemplo n.º 5
0
void main ()
{
  vBSP430platformInitialize_ni();
  vBSP430unittestInitialize();

  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(0x1234, BSP430_CORE_SWAP_16(0x3412));
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(0x1234, bswap16i16o16(0x3412));
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(0x1234, bswap16i32o32(0x3412));

  BSP430_UNITTEST_ASSERT_EQUAL_FMTlx(0x7856, BSP430_CORE_SWAP_16(0x12345678L));
  BSP430_UNITTEST_ASSERT_EQUAL_FMTlx(0x7856L, bswap16i32o32(0x12345678L));

  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(0xFEDC, BSP430_CORE_SWAP_16(0xDCFE));
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(0xFEDC, bswap16i16o16(0xDCFE));
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(0xFEDC, bswap16i32o32(0xDCFE));

  BSP430_UNITTEST_ASSERT_EQUAL_FMTlx(0x98BA, BSP430_CORE_SWAP_16(0xFEDCBA98));
  BSP430_UNITTEST_ASSERT_EQUAL_FMTlx(0x98BAL, bswap16i32o32(0xFEDCBA98L));

  vBSP430unittestFinalize();
}
Exemplo n.º 6
0
void main ()
{
  const sColor * cp = colors;
  const sColor * const ecp = colors + sizeof(colors) / sizeof(*colors);

  vBSP430platformInitialize_ni();
  (void)iBSP430consoleInitialize();
  while (1) {
    if (0 > cp->idx) {
      cprintf("%s is not available\n", cp->name);
    } else {
      vBSP430ledSet(cp->idx, 1);
      cprintf("%s lit; mask 0x%x\n", cp->name, read_leds());
      BSP430_CORE_DELAY_CYCLES(5 * BSP430_CLOCK_NOMINAL_MCLK_HZ);
      vBSP430ledSet(cp->idx, 0);
    }
    if (++cp == ecp) {
      cp = colors;
    }
  }
}
Exemplo n.º 7
0
void main ()
{
    int rv;
    uBSP430eui64 eui64;
    int i;

    vBSP430platformInitialize_ni();
    (void)iBSP430consoleInitialize();

    cputs("\n\n\nEUI-64 Verification");
#if ! (BSP430_EUI64 - 0)
    cputs("EUI-64 not supported by platform\n");
#else /* BSP430_EUI64 */
    while (1) {
        memset(&eui64, 0, sizeof(eui64));
        rv = iBSP430eui64(&eui64);
        cprintf("Request got %d: ", rv);
        for (i = 0; i < sizeof(eui64.bytes); ++i) {
            cprintf("%02x", eui64.bytes[i]);
        }
        cputchar('\n');
    }
#endif /* BSP430_EUI64 */
}
Exemplo n.º 8
0
void main ()
{
  BSP430_CORE_INTERRUPT_STATE_T istate;
#if BSP430_MODULE_SYS - 0
  unsigned long reset_causes = 0;
  unsigned int reset_flags = 0;
#endif /* BSP430_MODULE_SYS */

#if BSP430_MODULE_SYS - 0
  {
    unsigned int sysrstiv;

    /* Record all the reset causes */
    while (0 != ((sysrstiv = uiBSP430sysSYSRSTGenerator_ni(&reset_flags)))) {
      reset_causes |= 1UL << (sysrstiv / 2);
    }
  }
#endif /* BSP430_MODULE_SYS */

  vBSP430platformInitialize_ni();
  (void)iBSP430consoleInitialize();

#if BSP430_MODULE_SYS - 0
  cprintf("System reset bitmask %lx; causes:\n", reset_causes);
  {
    int bit = 0;
    while (bit < (8 * sizeof(reset_causes))) {
      if (reset_causes & (1UL << bit)) {
        cprintf("\t%s\n", xBSP430sysSYSRSTIVDescription(2*bit));
      }
      ++bit;
    }
  }

  cputtext_ni("System reset included:");
  if (reset_flags) {
    if (reset_flags & BSP430_SYS_FLAG_SYSRST_BOR) {
      cputtext_ni(" BOR");
    }
    if (reset_flags & BSP430_SYS_FLAG_SYSRST_LPM5WU) {
      cputtext_ni(" LPM5WU");
    }
    if (reset_flags & BSP430_SYS_FLAG_SYSRST_POR) {
      cputtext_ni(" POR");
    }
    if (reset_flags & BSP430_SYS_FLAG_SYSRST_PUC) {
      cputtext_ni(" PUC");
    }
  } else {
    cputtext_ni(" no data");
  }
  cputchar_ni('\n');
#endif /* BSP430_MODULE_SYS */

  BSP430_CORE_ENABLE_INTERRUPT();

  memcpy(ivect, VECTOR_OFFSET, VECTOR_LENGTH_BYTES);
  dumpRegion("Cached vectors", ivect, VECTOR_LENGTH_BYTES);
  dumpRegion("Vectors", VECTOR_OFFSET, VECTOR_LENGTH_BYTES);

  BSP430_CORE_SAVE_INTERRUPT_STATE(istate);
  BSP430_CORE_DISABLE_INTERRUPT();
  do {
    /* Note: You need to flush the console if you want to see the
     * output now; otherwise it'll be printed once interrupt-driven
     * transmission is re-enabled. */
    iBSP430consoleFlush();
    iBSP430consoleTransmitUseInterrupts_ni(0);
    (void)iBSP430flashEraseSegment_ni((void*)0xFE00);
    dumpRegion("Vectors with 0xFE00", VECTOR_OFFSET, VECTOR_LENGTH_BYTES);
    (void)iBSP430flashEraseSegment_ni(VECTOR_OFFSET);
    vBSP430ledSet(0, 1);
    dumpRegion("Vectors as erased", VECTOR_OFFSET, VECTOR_LENGTH_BYTES);
    memcpy(erased_ivect, VECTOR_OFFSET, VECTOR_LENGTH_BYTES);
    (void)iBSP430flashWriteData_ni(VECTOR_OFFSET, ivect, VECTOR_LENGTH_BYTES);
    vBSP430ledSet(1, 1);
    iBSP430consoleTransmitUseInterrupts_ni(1);
  } while (0);
  BSP430_CORE_RESTORE_INTERRUPT_STATE(istate);

  dumpRegion("Erased Vectors", erased_ivect, VECTOR_LENGTH_BYTES);
  dumpRegion("Restored Vectors", VECTOR_OFFSET, VECTOR_LENGTH_BYTES);
  iBSP430consoleFlush();
}
Exemplo n.º 9
0
void main ()
{
  int rc = 0;

  /* GDO0 and GDO2 are always interrupt-capable. */
  volatile sBSP430hplPORTIE * gdo0 = xBSP430hplLookupPORTIE(BSP430_RF_CC110X_GDO0_PORT_PERIPH_HANDLE);
  volatile sBSP430hplPORTIE * gdo2 = xBSP430hplLookupPORTIE(BSP430_RF_CC110X_GDO2_PORT_PERIPH_HANDLE);
  hBSP430halPORT hgdo1 = hBSP430portLookup(BSP430_RF_CC110X_GDO1_PORT_PERIPH_HANDLE);
  hBSP430halPORT hcsn = hBSP430portLookup(BSP430_RF_CC110X_CSn_PORT_PERIPH_HANDLE);

  spi = hBSP430serialLookup(BSP430_RF_CC110X_SPI_PERIPH_HANDLE);

  vBSP430platformInitialize_ni();
  (void)iBSP430consoleInitialize();
  cprintf("\nccid " __DATE__ " " __TIME__ "\n");

  cprintf("GDO0 %p at %s.%u\n", gdo0, xBSP430portName(BSP430_RF_CC110X_GDO0_PORT_PERIPH_HANDLE), iBSP430portBitPosition(BSP430_RF_CC110X_GDO0_PORT_BIT));
  cprintf("GDO1 HAL %p HPL %p at %s.%u\n", hgdo1, hgdo1->hpl.any, xBSP430portName(BSP430_RF_CC110X_GDO1_PORT_PERIPH_HANDLE), iBSP430portBitPosition(BSP430_RF_CC110X_GDO1_PORT_BIT));
  cprintf("GDO2 %p at %s.%u\n", gdo2, xBSP430portName(BSP430_RF_CC110X_GDO2_PORT_PERIPH_HANDLE), iBSP430portBitPosition(BSP430_RF_CC110X_GDO2_PORT_BIT));
  cprintf("CSn HAL %p HPL %p at %s.%u\n", hcsn, hcsn->hpl.any, xBSP430portName(BSP430_RF_CC110X_CSn_PORT_PERIPH_HANDLE), iBSP430portBitPosition(BSP430_RF_CC110X_CSn_PORT_BIT));
  cprintf("SPI %p is %s\n", spi, xBSP430serialName(BSP430_RF_CC110X_SPI_PERIPH_HANDLE));
#if BSP430_PLATFORM_PERIPHERAL_HELP
  cprintf("SPI Pins: %s\n", xBSP430platformPeripheralHelp(BSP430_RF_CC110X_SPI_PERIPH_HANDLE, BSP430_PERIPHCFG_SERIAL_SPI3));
#endif /* BSP430_PLATFORM_PERIPHERAL_HELP */
  cprintf(__DATE__ " " __TIME__ "\n");


  /* Configure the SPI interface, but immediately put it into hold
   * mode so we can check CHIP_RDYn on the MISO/GDO1 input. */
  spi = hBSP430serialOpenSPI(spi, BSP430_RF_CC110X_SPI_CTL0_BYTE, 0, 0);
  if (spi) {
    rc = iBSP430serialSetHold_rh(spi, 1);
    /* GDO1 to input, pull-up */
    BSP430_PORT_HAL_HPL_DIR(hgdo1) &= ~BSP430_RF_CC110X_GDO1_PORT_BIT;
    BSP430_PORT_HAL_SET_REN(hgdo1, BSP430_RF_CC110X_GDO1_PORT_BIT, BSP430_PORT_REN_PULL_UP);
  }

  cprintf("SPI device %p hold returned %d\n", spi, rc);
  if (! spi) {
    return;
  }

  /* Configure CSn initial high to ensure we have a falling edge when
   * we first enable the radio. */
  BSP430_PORT_HAL_HPL_SEL(hcsn) &= ~BSP430_RF_CC110X_CSn_PORT_BIT;
  BSP430_PORT_HAL_HPL_OUT(hcsn) |= BSP430_RF_CC110X_CSn_PORT_BIT;
  BSP430_PORT_HAL_HPL_DIR(hcsn) |= BSP430_RF_CC110X_CSn_PORT_BIT;

  /* Now enable the radio */
  BSP430_PORT_HAL_HPL_OUT(hcsn) &= ~BSP430_RF_CC110X_CSn_PORT_BIT;

  /* Spin until GDO1 (CHP_RDYn) is clear indicating radio is responsive */
  while (BSP430_PORT_HAL_HPL_IN(hgdo1) & BSP430_RF_CC110X_GDO1_PORT_BIT) {
    cprintf("Waiting for radio ready\n");
    BSP430_CORE_DELAY_CYCLES(BSP430_CLOCK_NOMINAL_MCLK_HZ);
  }

  /* Enable SPI */
  rc = iBSP430serialSetHold_rh(spi, 0);
  cprintf("Radio is up, hold release %d; sending SRES strobe\n", rc);

  /* Send a reset */
  do {
    rc = sendStrobe(0x30);
    cprintf("Strobe response %#02x\n", rc);
    if (0x0F != rc) {
      BSP430_CORE_DELAY_CYCLES(BSP430_CLOCK_NOMINAL_MCLK_HZ);
    }
  } while (0x0F != rc);

  cprintf("PARTNUM response %#02x\n", readRegister(0x30));
  cprintf("VERSION response %#02x\n", readRegister(0x31));
  cprintf("IOCFG2 read %#02x\n", readRegister(0x00));
  cprintf("IOCFG1 read %#02x\n", readRegister(0x01));
  cprintf("IOCFG0 read %#02x\n", readRegister(0x02));

  /* ChipCon radios consume 1.4mA when idle.  That goes down to
   * nominally 400 nA if the GDOs are configured to "HW to 0" and the
   * chip is told to power-down on loss of CSn.  On the EXP430F5438
   * the RF PWR header indicates that a CC1101 is using 40 nA in this
   * mode.*/
  rc = writeRegister(0x00, 0x2f);
  rc = writeRegister(0x01, 0x2f);
  rc = writeRegister(0x02, 0x2f);
  cprintf("Cleared IOCFG\n");
  cprintf("IOCFG2 read %#02x\n", readRegister(0x00));
  cprintf("IOCFG1 read %#02x\n", readRegister(0x01));
  cprintf("IOCFG0 read %#02x\n", readRegister(0x02));

  /* SPWD */
  rc = sendStrobe(0x39);
  cprintf("SPWD got %d\n", rc);

  /* Disable SPI before removing CSn otherwise the sequence isn't
   * right. */
  rc = iBSP430serialSetHold_rh(spi, 1);
  BSP430_PORT_HAL_HPL_OUT(hcsn) |= BSP430_RF_CC110X_CSn_PORT_BIT;

  /* This gets the RF2500T power down to about 120 nA.  Note:
   * Purposefully enter LPM with #GIE off since we do not intend to
   * wake up.*/
  BSP430_CORE_LPM_ENTER(LPM3_bits);
}
Exemplo n.º 10
0
void main ()
{
  hBSP430timerMuxSharedAlarm map;
  tBSP430periphHandle uptime_periph;
  int arc[sizeof(mux_alarms)/sizeof(*mux_alarms)];
  unsigned long last_wake_utt;
  unsigned long last_sleep_utt;
  int rc = 0;

  vBSP430platformInitialize_ni();
  last_wake_utt = ulBSP430uptime_ni();
  (void)iBSP430consoleInitialize();
  BSP430_CORE_ENABLE_INTERRUPT();

  cprintf("\n\nevent demo " __DATE__ " " __TIME__ "\n");
  mux_tag = ucBSP430eventTagAllocate("MuxAlarm");
  stats_tag = ucBSP430eventTagAllocate("Statistics");
  mux_flag = uiBSP430eventFlagAllocate();

  uptime_periph = xBSP430periphFromHPL(hBSP430uptimeTimer()->hpl);

  map = hBSP430timerMuxAlarmStartup(&mux_alarm_base, uptime_periph, UPTIME_MUXALARM_CCIDX);
  cprintf("Mux tag %u, stats tag %u, flag %x, with alarm base %p on %s.%u\n",
          mux_tag, stats_tag, mux_flag, map,
          xBSP430timerName(uptime_periph), UPTIME_MUXALARM_CCIDX);
  if (! map) {
    cprintf("ERR initializing mux shared alarm\n");
    goto err_out;
  }

  /* Processing done entirely in mux callback.  No wakeup. */
  mux_alarms[0].alarm.callback_ni = mux_alarm_callback;
  mux_alarms[0].interval_utt = BSP430_UPTIME_MS_TO_UTT(150);

  /* Processing done by an event flag */
  mux_alarms[1].alarm.callback_ni = mux_alarm_callback;
  mux_alarms[1].interval_utt = BSP430_UPTIME_MS_TO_UTT(500);
  mux_alarms[1].flag = mux_flag;

  /* Processing done by a callback with a timestamped event */
  mux_alarms[2].alarm.callback_ni = mux_alarm_callback;
  mux_alarms[2].interval_utt = BSP430_UPTIME_MS_TO_UTT(700);
  mux_alarms[2].process_fn = process_timestamp;
  mux_alarms[2].tag = mux_tag;

  /* Processing done by a callback with a timestamped event */
  mux_alarms[3].alarm.callback_ni = mux_alarm_callback;
  mux_alarms[3].interval_utt = BSP430_UPTIME_MS_TO_UTT(10000);
  mux_alarms[3].process_fn = process_statistics;
  mux_alarms[3].tag = stats_tag;

  /* Enable the multiplexed alarms */
  BSP430_CORE_DISABLE_INTERRUPT();
  do {
    int i = 0;
    for (i = 0; (0 == rc) && (i < sizeof(mux_alarms)/sizeof(*mux_alarms)); ++i) {
      mux_alarms[i].alarm.setting_tck = ulBSP430uptime_ni();
      arc[i] = iBSP430timerMuxAlarmAdd_ni(map, &mux_alarms[i].alarm);
    }
  } while (0);
  BSP430_CORE_ENABLE_INTERRUPT();

  /* Display the results.  All values should be non-negative for success. */
  {
    int i;
    cprintf("Alarm installation got:");
    rc = 0;
    for (i = 0; i < sizeof(arc)/sizeof(*arc); ++i) {
      cprintf(" %d", arc[i]);
      if (0 > arc[i]) {
        rc = arc[i];
      }
    }
    cputchar('\n');
  }
  if (0 > rc) {
    goto err_out;
  }

  last_sleep_utt = ulBSP430uptime();
  while (1) {
    last_wake_utt = ulBSP430uptime();
    unsigned int events = process_events(uiBSP430eventFlagsGet());
    if (events) {
      cprintf("ERR: Unprocessed event flags %04x\n", events);
    }

    BSP430_CORE_DISABLE_INTERRUPT();
    /* Put back any unprocessed events */
    vBSP430eventFlagsSet_ni(events);
    if (iBSP430eventFlagsEmpty_ni()) {
      /* Nothing pending: go to sleep, then jump back to the loop head
       * when we get woken. */
      statistics_v.sleep_utt += last_wake_utt - last_sleep_utt;
      last_sleep_utt = ulBSP430uptime_ni();
      statistics_v.awake_utt += last_sleep_utt - last_wake_utt;
      statistics_v.sleep_ct += 1;
      BSP430_CORE_LPM_ENTER_NI(LPM4_bits | GIE);
      continue;
    }
    BSP430_CORE_ENABLE_INTERRUPT();
  }
err_out:
  (void)iBSP430consoleFlush();
  return;
}
Exemplo n.º 11
0
void main ()
{
  sBSP430halPORT * port_hal;
  hBSP430halTIMER hal;
  volatile sBSP430hplTIMER * hpl;

  vBSP430platformInitialize_ni();
  (void)iBSP430consoleInitialize();
  cputchar('\n');
  BSP430_CORE_DELAY_CYCLES(BSP430_CLOCK_NOMINAL_MCLK_HZ / 1000);

  cprintf("\n\nsynccap " __DATE__ " " __TIME__ "\n");
  cprintf("External input on %s.%u corresponds to %s.%u%c\n",
          xBSP430portName(BSP430_TIMER_CCACLK_CC1_PORT_PERIPH_HANDLE),
          bitToPin(BSP430_TIMER_CCACLK_CC1_PORT_BIT),
          xBSP430timerName(BSP430_TIMER_CCACLK_PERIPH_HANDLE),
          PORT_CCIDX,
          'A' + (BSP430_TIMER_CCACLK_CC1_CCIS / CCIS0));
  port_hal = hBSP430portLookup(BSP430_TIMER_CCACLK_CC1_PORT_PERIPH_HANDLE);
  if (NULL == port_hal) {
    cprintf("Port HAL not available\n");
    return;
  }
  hal = hBSP430timerLookup(BSP430_TIMER_CCACLK_PERIPH_HANDLE);
  if (NULL == hal) {
    cprintf("Can't find timer\n");
    return;
  }

  BSP430_PORT_HAL_HPL_DIR(port_hal) &= ~BSP430_TIMER_CCACLK_CC1_PORT_BIT;
  BSP430_PORT_HAL_HPL_SEL(port_hal) |= BSP430_TIMER_CCACLK_CC1_PORT_BIT;
  hpl = hal->hpl;
  hpl->cctl[1] = CM_3 | BSP430_TIMER_CCACLK_CC1_CCIS | SCS | CAP | CCIE;
  captured.last_cci = !!(hpl->cctl[1] & CCI);
  BSP430_HAL_ISR_CALLBACK_LINK_NI(sBSP430halISRIndexedChainNode,
                                  hal->cc_cbchain_ni[PORT_CCIDX],
                                  captured.cb,
                                  next_ni);
  hpl->ctl = TASSEL_2 | MC_2 | TACLR | TAIE;

  /* Need to enable interrupts so timer overflow events are properly
   * acknowledged */
  while (1) {
    unsigned int ccr;
    unsigned int cctl;
    unsigned int count;
    unsigned int errors;
    int last_cci;
    unsigned long event_tt;

    BSP430_CORE_DISABLE_INTERRUPT();
    do {
      event_tt = captured.event_tt;
      captured.event_tt = 0;
      count = captured.count;
      errors = captured.errors;
      captured.count = 0;
      captured.errors = 0;
      last_cci = captured.last_cci;
      cctl = hpl->cctl[PORT_CCIDX];
      ccr = hpl->ccr[PORT_CCIDX];
      hpl->cctl[PORT_CCIDX] &= ~COV;
    } while (0);
    BSP430_CORE_ENABLE_INTERRUPT();

    cprintf("Up %lu ACLK ticks, timer %lu event %lx ccr %x cctl %04x\n"
            "\tCCI %d SCCI %d COV %d ; recorded CCI %d ; count %u errors %d\n",
            ulBSP430uptime(),
            ulBSP430timerCounter(hal, NULL),
            event_tt,
            ccr,
            cctl,
            !!(cctl & CCI), !!(cctl & SCCI), !!(cctl & COV), last_cci, count, errors);
    BSP430_CORE_DELAY_CYCLES(BSP430_CLOCK_NOMINAL_MCLK_HZ);
  }
}
Exemplo n.º 12
0
void main ()
{
  volatile sBSP430hplTIMER * const timer_hpl = xBSP430hplLookupTIMER(BSP430_TIMER_CCACLK_PERIPH_HANDLE);
  unsigned int outclk;
  unsigned int last_outclk;
  unsigned int cctl;
  hBSP430halPORT const inclk_port_hal = hBSP430portLookup(BSP430_TIMER_CCACLK_CLK_PORT_PERIPH_HANDLE);
  hBSP430halPORT const cc_port_hal = hBSP430portLookup(APP_CC_PORT_PERIPH_HANDLE);
  hBSP430halPORT const outclk_port_hal = hBSP430portLookup(APP_OUTCLK_PORT_PERIPH_HANDLE);
  hBSP430halPORT const trigger_port_hal = hBSP430portLookup(APP_TRIGGER_PORT_PERIPH_HANDLE);
  vBSP430platformInitialize_ni();
  vBSP430unittestInitialize();

  cprintf("timer_scs_test: " __DATE__ " " __TIME__ "\n");
  if (NULL == timer_hpl) {
    cprintf("ERROR: Unable to get timer HPL access\n");
    return;
  }
  if (NULL == inclk_port_hal) {
    cprintf("ERROR: Unable to get INCLK port access\n");
    return;
  }
  if (NULL == cc_port_hal) {
    cprintf("ERROR: Unable to get CC0 port access\n");
    return;
  }
  if (NULL == outclk_port_hal) {
    cprintf("ERROR: Unable to get OUTCLK port access\n");
    return;
  }
  if (NULL == trigger_port_hal) {
    cprintf("ERROR: Unable to get TRIGGER port access\n");
    return;
  }
  cprintf("Please connect OUTCLK at %s.%u to %s INCLK at %s.%u\n",
          xBSP430portName(APP_OUTCLK_PORT_PERIPH_HANDLE),
          iBSP430portBitPosition(APP_OUTCLK_PORT_BIT),
          xBSP430timerName(BSP430_TIMER_CCACLK_PERIPH_HANDLE),
          xBSP430portName(BSP430_TIMER_CCACLK_CLK_PORT_PERIPH_HANDLE),
          iBSP430portBitPosition(BSP430_TIMER_CCACLK_CLK_PORT_BIT));
  cprintf("Please connect TRIGGER at %s.%u to %s CCI0%c at %s.%u\n",
          xBSP430portName(APP_TRIGGER_PORT_PERIPH_HANDLE),
          iBSP430portBitPosition(APP_TRIGGER_PORT_BIT),
          xBSP430timerName(BSP430_TIMER_CCACLK_PERIPH_HANDLE),
          'A' + (APP_CC_CCIS / CCIS0),
          xBSP430portName(APP_CC_PORT_PERIPH_HANDLE),
          iBSP430portBitPosition(APP_CC_PORT_BIT));

  /* OUTCLK: output low */
  outclk = 0;
  BSP430_PORT_HAL_HPL_OUT(outclk_port_hal) &= ~APP_OUTCLK_PORT_BIT;
  BSP430_PORT_HAL_HPL_DIR(outclk_port_hal) |= APP_OUTCLK_PORT_BIT;
  BSP430_PORT_HAL_HPL_SEL(outclk_port_hal) &= ~APP_OUTCLK_PORT_BIT;

  /* TRIGGER: output low */
  BSP430_PORT_HAL_HPL_OUT(trigger_port_hal) &= ~APP_TRIGGER_PORT_BIT;
  BSP430_PORT_HAL_HPL_DIR(trigger_port_hal) |= APP_TRIGGER_PORT_BIT;
  BSP430_PORT_HAL_HPL_SEL(trigger_port_hal) &= ~APP_TRIGGER_PORT_BIT;

  /* INCLK: input peripheral function */
  BSP430_PORT_HAL_HPL_SEL(inclk_port_hal) &= ~BSP430_TIMER_CCACLK_CLK_PORT_BIT;
  BSP430_PORT_HAL_HPL_SEL(inclk_port_hal) |= BSP430_TIMER_CCACLK_CLK_PORT_BIT;

  /* CC0: input peripheral function */
  BSP430_PORT_HAL_HPL_DIR(cc_port_hal) &= ~APP_CC_PORT_BIT;
  BSP430_PORT_HAL_HPL_SEL(cc_port_hal) |= APP_CC_PORT_BIT;
  cprintf("P4: DIR %04x SEL %04x\n", P4DIR, P4SEL);

#define CLEAR_CAPTURE() do {                    \
    timer_hpl->cctl[APP_CCIDX] &= ~CCIFG;                 \
    timer_hpl->ccr[APP_CCIDX] = 0;                        \
  } while (0)

#define ASSERT_CLOCK_HIGH() do {                                        \
    BSP430_UNITTEST_ASSERT_TRUE(BSP430_PORT_HAL_HPL_OUT(outclk_port_hal) & APP_OUTCLK_PORT_BIT); \
  } while (0)

#define ASSERT_CLOCK_LOW() do {                                         \
    BSP430_UNITTEST_ASSERT_FALSE(BSP430_PORT_HAL_HPL_OUT(outclk_port_hal) & APP_OUTCLK_PORT_BIT); \
  } while (0)

#define ASSERT_CCI_HIGH() do {                              \
    BSP430_UNITTEST_ASSERT_TRUE(CCI & timer_hpl->cctl[APP_CCIDX]);        \
  } while (0)

#define ASSERT_CCI_LOW() do {                                \
    BSP430_UNITTEST_ASSERT_FALSE(CCI & timer_hpl->cctl[APP_CCIDX]);        \
  } while (0)

#define ASSERT_INTERNAL_TRIGGER_HIGH() do {                             \
    BSP430_UNITTEST_ASSERT_TRUE(CCIS_3 == (CCIS_3 & timer_hpl->cctl[APP_CCIDX])); \
  } while (0)

#define ASSERT_INTERNAL_TRIGGER_LOW() do {                              \
    BSP430_UNITTEST_ASSERT_TRUE(CCIS_2 == (CCIS_3 & timer_hpl->cctl[APP_CCIDX])); \
  } while (0)

#define ASSERT_NO_CAPTURE() do {                                \
    BSP430_UNITTEST_ASSERT_FALSE(CCIFG & timer_hpl->cctl[APP_CCIDX]);     \
    BSP430_UNITTEST_ASSERT_EQUAL_FMTx(0, timer_hpl->ccr[APP_CCIDX]);      \
  } while (0)

#define ASSERT_YES_CAPTURE() do {                                       \
    BSP430_UNITTEST_ASSERT_TRUE(CCIFG & timer_hpl->cctl[APP_CCIDX]);              \
    BSP430_UNITTEST_ASSERT_EQUAL_FMTx(timer_hpl->r, timer_hpl->ccr[APP_CCIDX]);   \
  } while (0)

  /* Capture asynchronously on falling edge from TRIGGER. */
  timer_hpl->ccr[APP_CCIDX] = 0;
  timer_hpl->cctl[APP_CCIDX] = CM_2 | APP_CC_CCIS | SCCI | CAP;
  timer_hpl->cctl[APP_CCIDX] = CM_3 | APP_CC_CCIS | SCCI | CAP;
  cprintf("%u: Timer: R %04x CTL %04x CCR %04x CCTL %04x\n", __LINE__, timer_hpl->r, timer_hpl->ctl, timer_hpl->ccr[APP_CCIDX], timer_hpl->cctl[APP_CCIDX]);

  /* Count upwards. */
  timer_hpl->ctl = TASSEL_0 | MC_2 | TACLR;

  /* Validate that we can control the clock input. */
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, timer_hpl->r);
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, 0);
  ASSERT_CLOCK_LOW();
  HALF_TICK_OUTCLK();
  ASSERT_CLOCK_HIGH();
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, 1);
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, timer_hpl->r);
  HALF_TICK_OUTCLK();
  ASSERT_CLOCK_LOW();
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, timer_hpl->r);
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, 1);
  HALF_TICK_OUTCLK();
  ASSERT_CLOCK_HIGH();
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, timer_hpl->r);
  HALF_TICK_OUTCLK();
  ASSERT_CLOCK_LOW();
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, timer_hpl->r);

  /* Verify that we can control the trigger, and that asynchronous
   * captures work. */
  ASSERT_NO_CAPTURE();
  ASSERT_CCI_LOW();
  HALF_TRIGGER();
  if (CM0 & timer_hpl->cctl[APP_CCIDX]) {
    ASSERT_YES_CAPTURE();
    if (! (CM1 & timer_hpl->cctl[APP_CCIDX])) {
      CLEAR_CAPTURE();
    }
  } else {
    ASSERT_NO_CAPTURE();
  }
  ASSERT_CCI_HIGH();
  HALF_TRIGGER();
  ASSERT_YES_CAPTURE();
  ASSERT_CCI_LOW();
  CLEAR_CAPTURE();

  /* Advance the clock.  Make sure no capture occurred. */
  last_outclk = outclk;
  HALF_TICK_OUTCLK();
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, last_outclk+1);
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, timer_hpl->r);
  ASSERT_NO_CAPTURE();
  last_outclk = outclk;
  HALF_TICK_OUTCLK();
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(last_outclk, timer_hpl->r);
  ASSERT_NO_CAPTURE();

  /* Now turn on synchronous capture */
  timer_hpl->cctl[APP_CCIDX] |= SCS;

  /* Advance the clock.  Make sure no capture occurred */
  cctl = timer_hpl->cctl[APP_CCIDX];
  last_outclk = outclk;
  ASSERT_CLOCK_LOW();
  HALF_TICK_OUTCLK();
  ASSERT_CLOCK_HIGH();
  ASSERT_NO_CAPTURE();
  HALF_TICK_OUTCLK();
  ASSERT_CLOCK_LOW();
  ASSERT_NO_CAPTURE();
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(last_outclk+1, timer_hpl->r);
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(cctl, timer_hpl->cctl[APP_CCIDX]);

  /* Do this again to make really sure no capture occurred. */
  HALF_TICK_OUTCLK();
  ASSERT_NO_CAPTURE();
  HALF_TICK_OUTCLK();
  ASSERT_NO_CAPTURE();
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(last_outclk+2, timer_hpl->r);
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(cctl, timer_hpl->cctl[APP_CCIDX]);

  /*
  F1) CCI rises then falls while CLK remains low.  CCIFG remains low.  When CLK
  rises the counter is incremented but CCIFG remains low.  CCIFG is set only
  when CLK falls.
  */

  /* CLK is low. */
  ASSERT_CLOCK_LOW();

  /* Check that external triggers with sync async do not trigger when
   * clock does not advance. */
  ASSERT_NO_CAPTURE();
  ASSERT_CCI_LOW();
  HALF_TRIGGER();
  ASSERT_NO_CAPTURE();
  ASSERT_CCI_HIGH();
  HALF_TRIGGER();
  ASSERT_NO_CAPTURE();
  ASSERT_CCI_LOW();

  /* Advance the clock.  No action on rising edge. */
  last_outclk = outclk;
  HALF_TICK_OUTCLK();
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, last_outclk+1);
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, timer_hpl->r);
  ASSERT_NO_CAPTURE();
  ASSERT_CCI_LOW();
  ASSERT_CLOCK_HIGH();

  /* Falling edge does not increment counter but does cause capture */
  last_outclk = outclk;
  HALF_TICK_OUTCLK();
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, last_outclk);
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, timer_hpl->r);
  ASSERT_YES_CAPTURE();
  ASSERT_CCI_LOW();
  CLEAR_CAPTURE();

  /*
  F2) CCI rises then falls while CLK remains high.  CCIFG remains low.  When
  CLK falls CCIFG is set.
  */

  /* Advance the clock.  No action on rising edge. */
  last_outclk = outclk;
  HALF_TICK_OUTCLK();
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, last_outclk+1);
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, timer_hpl->r);
  ASSERT_NO_CAPTURE();
  ASSERT_CCI_LOW();
  ASSERT_CLOCK_HIGH();

  /* Check that external triggers with sync async do not trigger when
   * clock does not advance. */
  ASSERT_NO_CAPTURE();
  ASSERT_CCI_LOW();
  HALF_TRIGGER();
  ASSERT_NO_CAPTURE();
  ASSERT_CCI_HIGH();
  HALF_TRIGGER();
  ASSERT_NO_CAPTURE();
  ASSERT_CCI_LOW();

  /* Falling edge does not increment counter but does cause capture */
  last_outclk = outclk;
  HALF_TICK_OUTCLK();
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, last_outclk);
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, timer_hpl->r);
  ASSERT_YES_CAPTURE();
  ASSERT_CCI_LOW();
  CLEAR_CAPTURE();

  /* Now test it with internal toggles.  First, asynchronous: */
  timer_hpl->cctl[APP_CCIDX] = CM_3 | CCIS_2 | SCCI | CAP;
  ASSERT_NO_CAPTURE();
  ASSERT_INTERNAL_TRIGGER_LOW();
  ASSERT_CCI_LOW();
  HALF_TRIGGER();
  ASSERT_CCI_LOW();
  ASSERT_NO_CAPTURE();
  INTERNAL_HALF_TRIGGER();
  ASSERT_CCI_HIGH();
  ASSERT_INTERNAL_TRIGGER_HIGH();
  ASSERT_YES_CAPTURE();
  CLEAR_CAPTURE();
  HALF_TRIGGER();
  ASSERT_CCI_HIGH();
  ASSERT_NO_CAPTURE();
  INTERNAL_HALF_TRIGGER();
  ASSERT_CCI_LOW();
  ASSERT_INTERNAL_TRIGGER_LOW();
  ASSERT_YES_CAPTURE();
  ASSERT_CCI_LOW();
  CLEAR_CAPTURE();

  /* Now synchronous */
  timer_hpl->cctl[APP_CCIDX] |= SCS;

  ASSERT_NO_CAPTURE();
  ASSERT_INTERNAL_TRIGGER_LOW();
  INTERNAL_HALF_TRIGGER();
  ASSERT_INTERNAL_TRIGGER_HIGH();
  ASSERT_NO_CAPTURE();
  INTERNAL_HALF_TRIGGER();
  ASSERT_INTERNAL_TRIGGER_LOW();
  ASSERT_NO_CAPTURE();

  /* Advance the clock.  No action on rising edge. */
  last_outclk = outclk;
  HALF_TICK_OUTCLK();
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, last_outclk+1);
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, timer_hpl->r);
  ASSERT_NO_CAPTURE();
  ASSERT_CCI_LOW();
  ASSERT_CLOCK_HIGH();

  /* Falling edge does not increment counter but does cause capture */
  last_outclk = outclk;
  HALF_TICK_OUTCLK();
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, last_outclk);
  BSP430_UNITTEST_ASSERT_EQUAL_FMTx(outclk, timer_hpl->r);
  ASSERT_YES_CAPTURE();
  ASSERT_CCI_LOW();
  CLEAR_CAPTURE();

  cprintf("%u: Timer: R %04x CTL %04x CCR %04x CCTL %04x\n", __LINE__, timer_hpl->r, timer_hpl->ctl, timer_hpl->ccr[APP_CCIDX], timer_hpl->cctl[APP_CCIDX]);
  vBSP430unittestFinalize();
}
Exemplo n.º 13
0
void main ()
{
  int rc;
  unsigned long uptime_ticks_per_sec;
  const struct sBSP430onewireBus * bus = &ds18b20;

  vBSP430platformInitialize_ni();

  (void)iBSP430consoleInitialize();
  cprintf("\nHere we go...\n");

  uptime_ticks_per_sec = ulBSP430uptimeConversionFrequency_Hz_ni();
  cprintf("Uptime now %lu with frequency %lu Hz\n",
          ulBSP430uptime_ni(), uptime_ticks_per_sec);

  cprintf("Monitoring DS18xx on %s.%u bit %x\n",
          xBSP430portName(BSP430_PORT_HAL_GET_PERIPH_HANDLE(APP_DS18B20_PORT_HAL)) ?: "P?",
          iBSP430portBitPosition(APP_DS18B20_BIT),
          APP_DS18B20_BIT);

  do {
    rc = iBSP430onewireReadSerialNumber(bus, &serial);
    if (0 != rc) {
      cprintf("ERROR: Failed to read serial number from DS18B20: %d\n", rc);
      BSP430_CORE_DELAY_CYCLES(BSP430_CLOCK_NOMINAL_MCLK_HZ);
    }
  } while (0 != rc);
  cprintf("DS18B20 serial number: %02x%02x%02x%02x%02x%02x\n",
          serial.id[0], serial.id[1], serial.id[2],
          serial.id[3], serial.id[4], serial.id[5]);

  while (1) {
    int rc;
    unsigned long start_tck;
    unsigned long end_tck;
    unsigned int duration_ms;
    unsigned int delay_count = 0;
    int t_c;

    start_tck = ulBSP430uptime_ni();
    rc = -1;
    if (0 == iBSP430onewireRequestTemperature_ni(bus)) {
      /* Wait for read to complete.  Each read is nominally 61
       * microseconds.  Conversion time can be as long as 750 ms if
       * 12-bit resolution is used.  (12-bit resolution is the
       * default.) */
      while (! iBSP430onewireReadBit_ni(bus)) {
        ++delay_count;
      }
      rc = iBSP430onewireReadTemperature_ni(bus, &t_c);
    }
    end_tck = ulBSP430uptime_ni();
    duration_ms = 1000 * (end_tck - start_tck) / uptime_ticks_per_sec;

    if (0 == rc) {
      cprintf("Temperature %d dCel or %d d[degF] in %u ms\n",
              (10 * t_c) / 16, BSP430_ONEWIRE_xCel_TO_ddegF(t_c), duration_ms);
    } else {
      cprintf("Measurement failed in %u ms\n", duration_ms);
    }

    /* You'd want to do this if you were going to sleep here */
    vBSP430onewireShutdown_ni(bus);
  }
}
Exemplo n.º 14
0
void main ()
{
    volatile sBSP430hplTIMER * const hpl = xBSP430hplLookupTIMER(BSP430_PERIPH_TA0);
    unsigned long ta0_Hz;
    unsigned int delta_ta0;
    const struct sLPMconfig * lcp = lpm_configs;
    const struct sLPMconfig * const elcp = lpm_configs + sizeof(lpm_configs)/sizeof(*lpm_configs);

    vBSP430platformInitialize_ni();
    (void)iBSP430consoleInitialize();

    TA0CTL = TASSEL_1 | MC_2 | TACLR;
    ta0_Hz = ulBSP430timerFrequency_Hz_ni(BSP430_PERIPH_TA0);

#if 0
    /* This sequence eliminates the wakeup delay on the MSP430F5438A.
     * The ramifications of doing this are to be found in the Power
     * Management Module and Supply Voltage Supervisor chapter of the
     * 5xx/6xx Family User's Guide, in the section "SVS and SVM
     * Performance Modes and Wakeup Times".
     *
     * Also check MCU errata related to the PMM.  THere are several that
     * appear relevant when changing the module from its power-up
     * state. */
    PMMCTL0_H = PMMPW_H;
#if 1
    /* This variant works */
    SVSMLCTL &= ~(SVSLE | SVMLE);
#else
    /* This appears to have no effect, though it should work. */
    SVSMLCTL |= SVSLFP;
#endif
    PMMCTL0_H = !PMMPW_H;
#endif

    BSP430_CORE_ENABLE_INTERRUPT();

    cputs("\n\nTimer LPM wake delay test\n");
    delta_ta0 = ta0_Hz / 4;
    cprintf("TA0 is at %lu Hz; sleep time %u ticks\n", ta0_Hz, delta_ta0);
    cprintf("Standard mode SR is %04x\n", __read_status_register());
    cprintf("SR bits: SCG0 %04x ; SCG1 %04x\n", SCG0, SCG1);
    cprintf("LPM exit from ISRs clears: %04x\n", BSP430_CORE_LPM_EXIT_MASK);

    cputs("LPMx   CCR0  CAP0  Delta0   CCR1  CAP1  Delta1   SR");
    while (lcp < elcp) {
        unsigned int tar;

        cprintf("%s: ", lcp->tag);
        BSP430_CORE_DISABLE_INTERRUPT();
        ta0r = 0;
        hpl->cctl[0] = CCIE;
        tar = uiBSP430timerAsyncCounterRead_ni(hpl);
        hpl->ccr[0] = tar + delta_ta0;
        BSP430_CORE_LPM_ENTER_NI(lcp->lpm_bits);
        cprintf("%5u %5u %5u    ", hpl->ccr[0], ta0r, ta0r-hpl->ccr[0]);

        BSP430_CORE_DISABLE_INTERRUPT();
        ta0r = 0;
        hpl->cctl[1] = CCIE;
        tar = uiBSP430timerAsyncCounterRead_ni(hpl);
        hpl->ccr[1] = tar + delta_ta0;
        BSP430_CORE_LPM_ENTER_NI(lcp->lpm_bits);
        cprintf("%5u %5u %5u    ", hpl->ccr[1], ta0r, ta0r-hpl->ccr[1]);

        cprintf("%04x\n", __read_status_register());
        ++lcp;
    }
    cprintf("Done\n");

}
Exemplo n.º 15
0
void main ()
{
  int rc;
  unsigned long next_wake_utt;
  unsigned long delta_wake_utt;

  vBSP430platformInitialize_ni();
  (void)iBSP430consoleInitialize();

  cprintf("\n\nadc demo, " __DATE__ " " __TIME__ "\n");

  delta_wake_utt = 2 * ulBSP430uptimeConversionFrequency_Hz();

  rc = initializeADC();
  cprintf("%s initialized, returned %d, ADC cal at %p, REF cal at %p\n",
#if defined(__MSP430_HAS_ADC10__)
          "ADC10"
#elif defined(__MSP430_HAS_ADC10_A__)
          "ADC10_A"
#elif defined(__MSP430_HAS_ADC10_B__)
          "ADC10_B"
#elif defined(__MSP430_HAS_ADC10_B4__)
          "ADC10_B (FR4xx)"
#elif defined(__MSP430_HAS_ADC12__)
          "ADC12"
#elif defined(__MSP430_HAS_ADC12_B__)
          "ADC12_B"
#elif defined(__MSP430_HAS_ADC12_PLUS__)
          "ADC12_PLUS"
#endif /* ADC */
          , rc, cal_adc, cal_ref);

#if HAVE_REF
  if (cal_ref) {
    cprintf("Reference factors:\n"
            "\t" REF_1pX_STR "V %u (0x%04x)\n"
            "\t2.0V %u (0x%04x)\n"
            "\t2.5V %u (0x%04x)\n",
            cal_ref->cal_adc_15vref_factor, cal_ref->cal_adc_15vref_factor,
            cal_ref->cal_adc_20vref_factor, cal_ref->cal_adc_20vref_factor,
            cal_ref->cal_adc_25vref_factor, cal_ref->cal_adc_25vref_factor);
  }
#endif /* HAVE_REF */
  if (cal_adc) {
    cprintf("ADC gain factor %d (0x%04x), offset %d\n",
            cal_adc->cal_adc_gain_factor, cal_adc->cal_adc_gain_factor,
            cal_adc->cal_adc_offset);
    cprintf("Temperature ranges:\n");
    cprintf("\t" REF_1pX_STR "V T30 %u T85 %u\n", cal_adc->cal_adc_15t30, cal_adc->cal_adc_15t85);
#if BSP430_TLV_IS_5XX
    cprintf("\t2.0V T30 %u T85 %u\n", cal_adc->cal_adc_20t30, cal_adc->cal_adc_20t85);
#endif /* BSP430_TLV_IS_5XX */
    cprintf("\t2.5V T30 %u T85 %u\n", cal_adc->cal_adc_25t30, cal_adc->cal_adc_25t85);
  }

  cprintf("Vmid channel %u, Temp channel %u"
#ifdef INCH_AUX
          ", Aux channel %u"
#endif /* INCH_AUX */
          "\n",
          INCH_VMID / INCH_BASE, INCH_TEMP / INCH_BASE
#ifdef INCH_AUX
          , INCH_AUX / INCH_BASE
#endif /* INCH_AUX */
         );

  next_wake_utt = ulBSP430uptime_ni();
  while (1) {
    char timestamp[BSP430_UPTIME_AS_TEXT_LENGTH];
    static const int refv[] = { REF_1pX, REF_2p0, REF_2p5 };
    static const char * const refv_str[] = { REF_1pX_STR, "2.0", "2.5" };
    static const int const nrefv = sizeof(refv)/sizeof(*refv);
    static const int inch[] = { INCH_TEMP,
                                INCH_VMID,
#if defined(INCH_AUX)
                                INCH_AUX,
#endif /* INCH_AUX */
                              };
    static const int const ninch = sizeof(inch)/sizeof(*inch);
    int valid = 0;
    sSample sample[sizeof(refv)/sizeof(*refv)][sizeof(inch)/sizeof(*inch)];
    int ri;
    int ii;

#define VALID(_ri,_ii) ((1 << (_ii)) << ((_ri) * nrefv))
#define ANY_VALID(_ri) (((1 << nrefv)-1) << ((_ri) * nrefv))

    for (ri = 0; ri < nrefv; ++ri) {
      if (0 == setReferenceVoltage(refv[ri])) {
        for (ii = 0; ii < ninch; ++ii) {
          if (0 == getSample(sample[ri]+ii, refv[ri], inch[ii])) {
            valid |= VALID(ri, ii);
          }
        }
      }
    }
    cprintf("%s: valid %x", xBSP430uptimeAsText(ulBSP430uptime_ni(), timestamp), valid);
    for (ri = 0; ri < nrefv; ++ri) {
      if (valid & ANY_VALID(ri)) {
        cprintf("\n\t%sV: ", refv_str[ri]);
        for (ii = 0; ii < ninch; ++ii) {
          if (VALID(ri, ii) & valid) {
            if (INCH_TEMP == inch[ii]) {
              displayTemperature(sample[ri] + ii);
            } else if (INCH_VMID == inch[ii]) {
              displayVmid(sample[ri] + ii);
            } else {
              displayVoltage(sample[ri] + ii);
            }
          }
        }
      }
    }
    cputchar('\n');
    next_wake_utt += delta_wake_utt;
    while (0 < lBSP430uptimeSleepUntil(next_wake_utt, LPM3_bits)) {
      /* nop */
    }
  }
}
Exemplo n.º 16
0
void main ()
{
  volatile sBSP430hplPORTIE * b0hpl;
  hBSP430halTIMER b0timer_hal;
  int b0pin = iBSP430portBitPosition(BSP430_PLATFORM_BUTTON0_PORT_BIT);
  struct sBSP430timerPulseCapture pulsecap_state;
  hBSP430timerPulseCapture pulsecap;
  unsigned long freq_Hz;
  int rc;

  vBSP430platformInitialize_ni();
  (void)iBSP430consoleInitialize();

  cprintf("\npulsecap " __DATE__ " " __TIME__ "\n");

  cprintf("There's supposed to be a button at %s.%u\n",
          xBSP430portName(BSP430_PLATFORM_BUTTON0_PORT_PERIPH_HANDLE),
          b0pin);
  b0hpl = xBSP430hplLookupPORTIE(BSP430_PLATFORM_BUTTON0_PORT_PERIPH_HANDLE);
  if (NULL == b0hpl) {
    cprintf("Guess it's not there.  Never mind.\n");
    return;
  }
  cprintf("Found it at %p.  Now looking for timer HAL.\n", b0hpl);
  b0timer_hal = hBSP430timerLookup(BUTTON0_TIMER_PERIPH_HANDLE);
  if (NULL == b0timer_hal) {
    cprintf("That's not there, though.  Going away now.\n");
    return;
  }
  vBSP430timerResetCounter_ni(b0timer_hal);
  b0timer_hal->hpl->ctl = TASSEL__SMCLK | MC__CONTINOUS | TBCLR | TBIE;
  vBSP430timerInferHints_ni(b0timer_hal);
  freq_Hz = ulBSP430timerFrequency_Hz_ni(BUTTON0_TIMER_PERIPH_HANDLE);

  cprintf("Cool, we're good to go with a %lu Hz timer at %p, now %lu.\n",
          freq_Hz, b0timer_hal, ulBSP430timerCounter_ni(b0timer_hal, NULL));

  /* Configure the port for its primary peripheral function */
  b0hpl->dir &= ~BSP430_PLATFORM_BUTTON0_PORT_BIT;
  BSP430_PORT_HPL_SET_REN(b0hpl, BSP430_PLATFORM_BUTTON0_PORT_BIT, BSP430_PORT_REN_PULL_UP);
  BSP430_PORT_HPL_SET_SEL(b0hpl, BSP430_PLATFORM_BUTTON0_PORT_BIT, 1);

  pulsecap = hBSP430timerPulseCaptureInitialize(&pulsecap_state,
                                                BUTTON0_TIMER_PERIPH_HANDLE,
                                                BUTTON0_TIMER_CCIDX,
                                                BUTTON0_TIMER_CCIS,
                                                BSP430_TIMER_PULSECAP_START_CALLBACK | BSP430_TIMER_PULSECAP_END_CALLBACK,
                                                pulsecap_callback_ni);
  if (NULL == pulsecap) {
    cprintf("Sorry, pulsecap initialization failed\n");
    return;
  }
  cprintf("%s.%u%c cctl %04x; pulsecap %p flags %04x\n",
          xBSP430timerName(BUTTON0_TIMER_PERIPH_HANDLE),
          BUTTON0_TIMER_CCIDX,
          'A' + (BUTTON0_TIMER_CCIS / CCIS0),
          b0timer_hal->hpl->cctl[BUTTON0_TIMER_CCIDX],
          pulsecap, pulsecap->flags_ni);

  /* Need to enable interrupts so timer overflow events are properly
   * acknowledged */
  BSP430_CORE_ENABLE_INTERRUPT();

  rc = iBSP430timerPulseCaptureEnable(pulsecap);
  cprintf("Enable got %d\n", rc);
  rc = iBSP430timerPulseCaptureActivate(pulsecap);
  cprintf("Activate got %d\n", rc);
  while (1) {
    unsigned int flags;
    unsigned long pulseWidth_tt;
    unsigned int overflows;
    unsigned int activehighs;

    BSP430_CORE_DISABLE_INTERRUPT();
    do {
      flags = pulsecap_state.flags_ni;
      pulseWidth_tt = pulseWidth_tt_v;
      overflows = overflows_v;
      activehighs = activehighs_v;
    } while (0);
    BSP430_CORE_ENABLE_INTERRUPT();
    cprintf("Timer %lu flags %04x ; %u over %u activehigh\n",
            ulBSP430timerCounter(b0timer_hal, NULL),
            flags, overflows, activehighs);
    if (0 != pulseWidth_tt) {
      cprintf("\tNew width: %lu ticks = %lu us\n", pulseWidth_tt,
              (unsigned long)((1000ULL * pulseWidth_tt) / (freq_Hz / 1000UL)));
      pulseWidth_tt = 0;
    }
    BSP430_CORE_DELAY_CYCLES(BSP430_CLOCK_NOMINAL_MCLK_HZ);
  }
}
Exemplo n.º 17
0
void main ()
{
  /* First thing you do in main is configure the platform. */
  vBSP430platformInitialize_ni();
  /* And that's all this one does. */
}
Exemplo n.º 18
0
void main ()
{
  int rc;
  sBSP430m25p m25p_data;
  hBSP430m25p m25p;
  unsigned long addr;
  unsigned long t0;
  unsigned long t1;

  vBSP430platformInitialize_ni();
  (void)iBSP430consoleInitialize();

  cprintf("\nBuild " __DATE__ " " __TIME__ "\n");
  cprintf("SPI is %s: %s\n",
          xBSP430serialName(BSP430_PLATFORM_M25P_SPI_PERIPH_HANDLE),
          xBSP430platformPeripheralHelp(BSP430_PLATFORM_M25P_SPI_PERIPH_HANDLE, 0));

#ifdef BSP430_PLATFORM_M25P_PWR_PORT_PERIPH_HANDLE
  cprintf("PWR at %s.%u\n",
          xBSP430portName(BSP430_PLATFORM_M25P_PWR_PORT_PERIPH_HANDLE),
          iBSP430portBitPosition(BSP430_PLATFORM_M25P_PWR_PORT_BIT));
#else /* BSP430_PLATFORM_M25P_PWR_PORT_PERIPH_HANDLE */
  cprintf("PWR is hard-wired\n");
#endif /* BSP430_PLATFORM_M25P_PWR_PORT_PERIPH_HANDLE */

#ifdef BSP430_PLATFORM_M25P_RSTn_PORT_PERIPH_HANDLE
  cprintf("RSTn at %s.%u\n",
          xBSP430portName(BSP430_PLATFORM_M25P_RSTn_PORT_PERIPH_HANDLE),
          iBSP430portBitPosition(BSP430_PLATFORM_M25P_RSTn_PORT_BIT));
#else /* BSP430_PLATFORM_M25P_RSTn_PORT_PERIPH_HANDLE */
  cprintf("RSTn is hard-wired\n");
#endif /* BSP430_PLATFORM_M25P_RSTn_PORT_PERIPH_HANDLE */
  cprintf("CSn at %s.%u\n",
          xBSP430portName(BSP430_PLATFORM_M25P_CSn_PORT_PERIPH_HANDLE),
          iBSP430portBitPosition(BSP430_PLATFORM_M25P_CSn_PORT_BIT));

  memset(&m25p_data, 0, sizeof(m25p_data));
  m25p_data.spi = hBSP430serialLookup(BSP430_PLATFORM_M25P_SPI_PERIPH_HANDLE);
  m25p_data.csn_port = xBSP430hplLookupPORT(BSP430_PLATFORM_M25P_CSn_PORT_PERIPH_HANDLE);
  m25p_data.csn_bit = BSP430_PLATFORM_M25P_CSn_PORT_BIT;
#ifdef BSP430_PLATFORM_M25P_RSTn_PORT_PERIPH_HANDLE
  m25p_data.rstn_port = xBSP430hplLookupPORT(BSP430_PLATFORM_M25P_RSTn_PORT_PERIPH_HANDLE);
  m25p_data.rstn_bit = BSP430_PLATFORM_M25P_RSTn_PORT_BIT;
#endif /* BSP430_PLATFORM_M25P_RSTn_PORT_PERIPH_HANDLE */

  m25p = hBSP430m25pInitialize(&m25p_data,
                               BSP430_SERIAL_ADJUST_CTL0_INITIALIZER(UCCKPL | UCMSB | UCMST),
                               UCSSEL_2, 1);
  if (NULL == m25p) {
    cprintf("M25P device initialization failed.\n");
    return;
  }

#ifdef BSP430_PLATFORM_M25P_PWR_PORT_PERIPH_HANDLE
  {
    volatile sBSP430hplPORT * pwr_hpl;
    /* Turn on power, then wait 10 ms for chip to stabilize before releasing RSTn. */
    pwr_hpl = xBSP430hplLookupPORT(BSP430_PLATFORM_M25P_PWR_PORT_PERIPH_HANDLE);
    pwr_hpl->out &= ~BSP430_PLATFORM_M25P_PWR_PORT_BIT;
    pwr_hpl->dir |= BSP430_PLATFORM_M25P_PWR_PORT_BIT;
    pwr_hpl->out |= BSP430_PLATFORM_M25P_PWR_PORT_BIT;
    BSP430_CORE_DELAY_CYCLES(10 * (BSP430_CLOCK_NOMINAL_MCLK_HZ / 1000));
  }
#endif /* BSP430_PLATFORM_M25P_PWR_PORT_PERIPH_HANDLE */
  BSP430_M25P_RESET_CLEAR(m25p);

  cprintf("Status register %d\n", iBSP430m25pStatus_ni(m25p));
  rc = iBSP430m25pStrobeCommand_ni(m25p, BSP430_M25P_CMD_WREN);
  cprintf("WREN got %d, status register %d\n", rc, iBSP430m25pStatus_ni(m25p));
  rc = iBSP430m25pStrobeCommand_ni(m25p, BSP430_M25P_CMD_WRDI);
  cprintf("WRDI got %d, status register %d\n", rc, iBSP430m25pStatus_ni(m25p));

  rc = iBSP430m25pInitiateCommand_ni(m25p, BSP430_M25P_CMD_RDID);
  if (0 == rc) {
    rc = iBSP430m25pCompleteTxRx_ni(m25p, NULL, 0, 20, buffer);
  }

  BSP430_CORE_ENABLE_INTERRUPT();
  cprintf("READ_IDENTIFICATION got %d\n", rc);
  if (0 <= rc) {
    dumpMemory(buffer, rc, 0);
  }
  cprintf("Config identified %u sectors of %lu bytes each: %lu bytes total\n",
          BSP430_PLATFORM_M25P_SECTOR_COUNT,
          (unsigned long)BSP430_PLATFORM_M25P_SECTOR_SIZE,
          BSP430_PLATFORM_M25P_SECTOR_COUNT * (unsigned long)BSP430_PLATFORM_M25P_SECTOR_SIZE);
#if (BSP430_PLATFORM_M25P_SUBSECTOR_SIZE - 0)
  cprintf("Config supports access as %u sub-sectors of %u bytes each\n",
          (unsigned int)(BSP430_PLATFORM_M25P_SECTOR_COUNT * (BSP430_PLATFORM_M25P_SECTOR_SIZE / BSP430_PLATFORM_M25P_SUBSECTOR_SIZE)),
          (unsigned int)BSP430_PLATFORM_M25P_SUBSECTOR_SIZE);
#else /* BSP430_PLATFORM_M25P_SUBSECTOR_SIZE */
  cprintf("Config indicates device is not sub-sector addressable\n");
#endif /* BSP430_PLATFORM_M25P_SUBSECTOR_SIZE */
  cprintf("RDID identified %lu bytes total capacity\n", 0x1UL << buffer[2]);

  addr = 0;

  rc = readFromAddress(m25p, addr, sizeof(flashContents));
  if (sizeof(flashContents) != rc) {
    cprintf("ERROR %d reading initial block\n", rc);
  } else {
    dumpMemory(buffer, rc, addr);
    if (0 == memcmp(flashContents, buffer, rc)) {
      cprintf("Found expected contents.\n");
    }
  }

#if (BSP430_PLATFORM_M25P_SUPPORTS_PE - 0)
  rc = writeToAddress(m25p, BSP430_M25P_CMD_PE, addr, NULL, 0);
  cprintf("PAGE_ERASE got %d\n", rc);
#else /* BSP430_PLATFORM_M25P_SUPPORTS_PE */
  rc = writeToAddress(m25p, BSP430_M25P_CMD_SE, addr, NULL, 0);
  cprintf("SECTOR_ERASE got %d\n", rc);
#endif /* BSP430_PLATFORM_M25P_SUPPORTS_PE */
  rc = readFromAddress(m25p, addr, sizeof(buffer));
  if (0 < rc) {
    dumpMemory(buffer, rc, addr);
  }

  rc = writeToAddress(m25p, BSP430_M25P_CMD_PP, addr, flashContents, sizeof(flashContents));
  cprintf("PAGE_PROGRAM got %d\n", rc);
  rc = readFromAddress(m25p, addr, sizeof(buffer));
  if (0 < rc) {
    dumpMemory(buffer, rc, addr);
  }

  /* PAGE PROGRAM is the one that only clears 1s to 0s so needs a
   * prior page or sector erase */
  rc = writeToAddress(m25p, BSP430_M25P_CMD_PP, addr, flashContents + 4, 4);
  cprintf("PAGE_PROGRAM to %lx returned %d\n", addr, rc);
  rc = readFromAddress(m25p, 0, sizeof(flashContents));
  dumpMemory(buffer, rc, 0);
  /*
  Write 4 took 8
  PAGE_PROGRAM to 0 returned 4
  00000000  88 11 03 30 cc 33 c3 3c  01 23 45 67 89 ab cd ef  ...0.3.<.#Eg....
  */

  /* PAGE_WRITE is the one that does not need a prior erase cycle */
  addr = 8;
#if (BSP430_PLATFORM_M25P_SUPPORTS_PW - 0)
  rc = writeToAddress(m25p, BSP430_M25P_CMD_PW, addr, flashContents + 4, 4);
  cprintf("PAGE_WRITE to %lx returned %d\n", addr, rc);
#else
  rc = writeToAddress(m25p, BSP430_M25P_CMD_PP, addr, flashContents + 4, 4);
  cprintf("overwrite PAGE_PROGRAM to unerased %lx returned %d\n", addr, rc);
#endif
  rc = readFromAddress(m25p, 0, sizeof(flashContents));
  dumpMemory(buffer, rc, 0);
  /*
  Write 4 took 204
  PAGE_WRITE to 8 returned 4
  00000000  88 11 03 30 cc 33 c3 3c  cc 33 c3 3c 89 ab cd ef  ...0.3.<.3.<....
  */

  cprintf("Initiating bulk erase...");
  BSP430_CORE_DISABLE_INTERRUPT();
  do {
    t0 = t1 = 0;
    rc = iBSP430m25pStrobeCommand_ni(m25p, BSP430_M25P_CMD_WREN);
    if (0 == rc) {
      rc = iBSP430m25pStrobeCommand_ni(m25p, BSP430_M25P_CMD_BE);
    }
    if (0 == rc) {
      int sr;

      t0 = ulBSP430uptime_ni();
      do {
        sr = iBSP430m25pStatus_ni(m25p);
      } while ((0 <= sr) && (BSP430_M25P_SR_WIP & sr));
      t1 = ulBSP430uptime();
    }
  } while (0);
  BSP430_CORE_ENABLE_INTERRUPT();
  cprintf("\nBULK_ERASE got %d\n", rc);
  if (0 == rc) {
    char tstr[BSP430_UPTIME_AS_TEXT_LENGTH];
    cprintf("Bulk erase took %lu utt = %s\n", t1-t0, xBSP430uptimeAsText(t1 - t0, tstr));
  }
  rc = readFromAddress(m25p, 0, sizeof(flashContents));
  dumpMemory(buffer, rc, 0);

  rc = writeToAddress(m25p, BSP430_M25P_CMD_PP, 0, flashContents, sizeof(flashContents));
  cprintf("Restore got %d\n", rc);

  addr = 0;
  while (addr < (256 * 1025L)) {
    rc = readFromAddress(m25p, addr, sizeof(buffer));
    if (0 > rc) {
      break;
    }
    dumpMemory(buffer, rc, addr);
    addr += rc;
    break;
  }

}
Exemplo n.º 19
0
void main ()
{
  const char * command;
  int flags;

  vBSP430platformInitialize_ni();
  (void)iBSP430consoleInitialize();
  vBSP430cliSetDiagnosticFunction(iBSP430cliConsoleDiagnostic);
  cprintf("\ncli example " __DATE__ " " __TIME__ "\n");
#if configBSP430_CLI_COMMAND_COMPLETION - 0
  cprintf("Command completion is available.\n");
#endif /* configBSP430_CLI_COMMAND_COMPLETION */
  vBSP430ledSet(0, 1);
  cprintf("\nLED lit when not awaiting input\n");

  /* NOTE: The control flow in this is a bit tricky, as we're trying
   * to leave interrupts enabled during the main body of the loop,
   * while they must be disabled when processing input to recognize a
   * command.  The flags variable preserves state across multiple loop
   * iterations until all relevant activities have completed. */
  commandSet = LAST_COMMAND;
  command = NULL;
  flags = eBSP430cliConsole_REPAINT;

  BSP430_CORE_ENABLE_INTERRUPT();
  while (1) {
    if (flags & eBSP430cliConsole_ANY_ESCAPE) {
      int c;
      while (0 <= ((c = cgetchar()))) {
        cprintf("escape char 0x%02x (%u) '%c'\n", c, c, isprint(c) ? c : '.');
        /* Technically CSI is a single character 0x9b representing
         * ESC+[.  In the two-character mode accepted here, we use the
         * value for the second character. */
#define KEY_CSI '['
        if ((KEY_CSI == c) && (flags & eBSP430cliConsole_PROCESS_ESCAPE)) {
          flags &= ~eBSP430cliConsole_PROCESS_ESCAPE;
          flags |= eBSP430cliConsole_IN_ESCAPE;
        } else if ((64 <= c) && (c <= 126)) {
          flags &= ~eBSP430cliConsole_ANY_ESCAPE;
          cprintf("Leaving escape mode\n");
          break;
        }
      }
    }
    if (flags & eBSP430cliConsole_DO_COMPLETION) {
      flags &= ~eBSP430cliConsole_DO_COMPLETION;
      flags |= iBSP430cliConsoleBufferCompletion(commandSet, &command);
    }
    if (flags & eBSP430cliConsole_READY) {
      int rv;

      rv = iBSP430cliExecuteCommand(commandSet, 0, command);
      if (0 != rv) {
        cprintf("Command execution returned %d\n", rv);
      }
      /* Ensure prompt is rewritten, but not the command we just
       * ran */
      flags |= eBSP430cliConsole_REPAINT;
      command = NULL;
    }
    if (flags & eBSP430cliConsole_REPAINT) {
      /* Draw the prompt along with whatever's left in the command
       * buffer.  Note use of leading carriage return in case an edit
       * left material on the current line. */
      cprintf("\r> %s", command ? command : "");
      flags &= ~eBSP430cliConsole_REPAINT;
    }
    if (flags & eBSP430cliConsole_REPAINT_BEL) {
      cputchar('\a');
      flags &= ~eBSP430cliConsole_REPAINT_BEL;
    }
    BSP430_CORE_DISABLE_INTERRUPT();
    do {
      if (flags & eBSP430cliConsole_READY) {
        /* Clear the command we just completed */
        vBSP430cliConsoleBufferClear_ni();
        flags &= ~eBSP430cliConsole_READY;
      }
      do {
        /* Unless we're processing application-specific escape
         * characters let iBSP430cliConsoleBufferProcessInput_ni()
         * process any input characters that have already been
         * received. */
        if (! (flags & eBSP430cliConsole_ANY_ESCAPE)) {
          flags |= iBSP430cliConsoleBufferProcessInput_ni();
        }
        if (0 == flags) {
          /* Sleep until something wakes us, such as console input.
           * Then turn off interrupts and loop back to read that
           * input. */
          vBSP430ledSet(0, 0);
          BSP430_CORE_LPM_ENTER_NI(LPM0_bits);
          BSP430_CORE_DISABLE_INTERRUPT();
          vBSP430ledSet(0, 1);
        }
        /* Repeat if still nothing to do */
      } while (! flags);

      /* Got something to do; get the command contents in place so
       * we can update the screen. */
      command = xBSP430cliConsoleBuffer_ni();
    } while (0);
    BSP430_CORE_ENABLE_INTERRUPT();
  }
}
Exemplo n.º 20
0
void main ()
{
  hBSP430halSERIAL i2c;
  sBSP430bq24210 bq24210;
  union {
    sBQ27510 state;
    uint16_t raw[1];
  } u;
  const int nwords = sizeof(u.state)/sizeof(u.raw[0]);
  unsigned long resample_interval_utt;
  unsigned long resample_wake_utt;
  unsigned int flags;
  int rc;

  vBSP430platformInitialize_ni();
  (void)iBSP430consoleInitialize();

  cprintf("\nbattpack " __DATE__ " " __TIME__ "\n");

  bq24210.chg_port = xBSP430hplLookupPORT(APP_CHGn_PORT_PERIPH_HANDLE);
  bq24210.en_port = xBSP430hplLookupPORT(APP_ENn_PORT_PERIPH_HANDLE);
  bq24210.pg_port = xBSP430hplLookupPORT(APP_PGn_PORT_PERIPH_HANDLE);
  bq24210.chg_bit = APP_CHGn_PORT_BIT;
  bq24210.en_bit = APP_ENn_PORT_BIT;
  bq24210.pg_bit = APP_PGn_PORT_BIT;

  cprintf("CHGn on %s.%u\n",
          xBSP430portName(xBSP430periphFromHPL(bq24210.chg_port)),
          iBSP430portBitPosition(bq24210.chg_bit));
  cprintf("ENn on %s.%u\n",
          xBSP430portName(xBSP430periphFromHPL(bq24210.en_port)),
          iBSP430portBitPosition(bq24210.en_bit));
  cprintf("PGn on %s.%u\n",
          xBSP430portName(xBSP430periphFromHPL(bq24210.pg_port)),
          iBSP430portBitPosition(bq24210.pg_bit));
  if (! (bq24210.chg_port && bq24210.en_port && bq24210.pg_port)) {
    cprintf("One of the ports is missing\n");
    return;
  }

  /* Charge signal is an input (active low) to the MCU.  Configure as
   * input with internal pull-up. */
  bq24210.chg_port->dir &= ~bq24210.chg_bit;
  bq24210.chg_port->out |= bq24210.chg_bit;
  bq24210.chg_port->ren |= bq24210.chg_bit;

  /* Power-good signal is an input (active low) to the MCU.  Configure
   * as input with internal pull-up. */
  bq24210.pg_port->dir &= ~bq24210.pg_bit;
  bq24210.pg_port->out |= bq24210.pg_bit;
  bq24210.pg_port->ren |= bq24210.pg_bit;

  /* Enable signal is an output (active low) from the MCU.  Start
   * active. */
  bq24210.en_port->out &= ~bq24210.en_bit;
  bq24210.en_port->dir |= bq24210.en_bit;

  cprintf("I2C on %s at address 0x%02x\nPins: %s\n",
          xBSP430serialName(APP_BQ27510_I2C_PERIPH_HANDLE),
          APP_BQ27510_I2C_ADDRESS,
          xBSP430platformPeripheralHelp(APP_BQ27510_I2C_PERIPH_HANDLE, BSP430_PERIPHCFG_SERIAL_I2C));

  /* NOTE: At default BSP430_SERIAL_I2C_BUS_SPEED_HZ 400kHz this
   * devices supports only single-byte write operations.  Further,
   * ensure a 66us delay between packets. */
  i2c = hBSP430serialOpenI2C(hBSP430serialLookup(APP_BQ27510_I2C_PERIPH_HANDLE),
                             BSP430_SERIAL_ADJUST_CTL0_INITIALIZER(UCMST),
                             0, 0);
  if (! i2c) {
    cprintf("I2C open failed\n");
    return;
  }
  (void)iBSP430i2cSetAddresses_rh(i2c, -1, APP_BQ27510_I2C_ADDRESS);

  resample_interval_utt = BSP430_UPTIME_MS_TO_UTT(1000UL * RESAMPLE_INTERVAL_S);
  resample_wake_utt = ulBSP430uptime_ni();
  flags = FLG_DUMP_STATE | FLG_UPDATE_INTERVAL;

  BSP430_CORE_ENABLE_INTERRUPT();
  while (1) {
    char astext_buf[BSP430_UPTIME_AS_TEXT_LENGTH];
    uint16_t temperature_dC;

    if (FLG_DUMP_STATE & flags) {
      memset(&u, 0, sizeof(u));
      rc = readBQ27510(i2c, 0, nwords, u.raw);
      cprintf("Device ID %04x rc %d\n", u.state.device_id, rc);
      cprintf("%.30s = %d\n", "atRate_mA", u.state.atRate_mA);
      cprintf("%.30s = %u\n", "atRatetimeToEmpty_min", u.state.atRatetimeToEmpty_min);
      cprintf("%.30s = %u\n", "temperature_dK", u.state.temperature_dK);
      cprintf("%.30s = %u\n", "voltage_mV", u.state.voltage_mV);
      cprintf("%.30s = 0x%04x\n", "flags", u.state.flags);
      cprintf("%.30s = %u\n", "nominalAvailableCapacity_mAh", u.state.nominalAvailableCapacity_mAh);
      cprintf("%.30s = %u\n", "fullAvailableCapacity_mAh", u.state.fullAvailableCapacity_mAh);
      cprintf("%.30s = %u\n", "remainingCapacity_mAh", u.state.remainingCapacity_mAh);
      cprintf("%.30s = %u\n", "fullChargeCapacity_mAh", u.state.fullChargeCapacity_mAh);
      cprintf("%.30s = %d\n", "averageCurrent_mA", u.state.averageCurrent_mA);
      cprintf("%.30s = %u\n", "timeToEmpty_min", u.state.timeToEmpty_min);
      cprintf("%.30s = %d\n", "standbyCurrent_mA", u.state.standbyCurrent_mA);
      cprintf("%.30s = %u\n", "standbyTimeToEmpty_min", u.state.standbyTimeToEmpty_min);
      cprintf("%.30s = %u\n", "stateOfHealth_ppcpx", u.state.stateOfHealth_ppcpx);
      cprintf("%.30s = %u\n", "cycleCount", u.state.cycleCount);
      cprintf("%.30s = %u\n", "stateOfCharge_ppc", u.state.stateOfCharge_ppc);
      cprintf("%.30s = %d\n", "instantaneousCurrent_mA", u.state.instantaneousCurrent_mA);
      cprintf("%.30s = %u\n", "internalTemperature_dK", u.state.internalTemperature_dK);
      cprintf("%.30s = %u\n", "reistanceScale", u.state.reistanceScale);
      cprintf("%.30s = %u\n", "operationConfiguration", u.state.operationConfiguration);
      cprintf("%.30s = %u\n", "designCapacity_mAh", u.state.designCapacity_mAh);
      cprintf("flags %02x ; ENn state %d\n", flags, (bq24210.en_port->out & bq24210.en_bit));
      flags &= ~FLG_DUMP_STATE;
    }
    if (FLG_TOGGLE_ENABLE & flags) {
      bq24210.en_port->out ^= bq24210.en_bit;
      flags &= ~FLG_TOGGLE_ENABLE;
    }
    vBSP430ledSet(BSP430_LED_GREEN, !(bq24210.en_port->out & bq24210.en_bit));

    rc = readBQ27510(i2c, 0, nwords, u.raw);
    temperature_dC = u.state.temperature_dK - 2733;

    cprintf("%s: %c%c%c % 2d.%dC  %4dmV ; SoC %u%% ; Cap %4d / %4d ; %dmA ~ %dmA / %u\n",
            xBSP430uptimeAsText(ulBSP430uptime(), astext_buf),
            (bq24210.en_port->out & bq24210.en_bit) ? ' ' : 'E',
            (bq24210.chg_port->in & bq24210.chg_bit) ? ' ' : 'C',
            (bq24210.pg_port->in & bq24210.pg_bit) ? ' ' : 'P',
            (temperature_dC / 10), (temperature_dC % 10),
            u.state.voltage_mV,
            u.state.stateOfCharge_ppc,
            u.state.remainingCapacity_mAh,
            u.state.fullAvailableCapacity_mAh,
            u.state.instantaneousCurrent_mA,
            u.state.averageCurrent_mA,
            u.state.cycleCount
            );
    if (FLG_UPDATE_INTERVAL & flags) {
      resample_wake_utt += resample_interval_utt;
      flags &= ~FLG_UPDATE_INTERVAL;
    }
    flags = 0;
    while (! flags) {
      iBSP430consoleFlush();
      if (0 >= lBSP430uptimeSleepUntil(resample_wake_utt, LPM3_bits)) {
        flags |= FLG_UPDATE_INTERVAL;
      }
      while (0 <= ((rc = cgetchar()))) {
        if ('!' == rc) {
          flags |= FLG_TOGGLE_ENABLE;
        } else if (' ' == rc) {
          flags |= FLG_DUMP_STATE;
        }
      }
    }

  }
}
Exemplo n.º 21
0
void main ()
{
  hBSP430halSERIAL i2c = hBSP430serialLookup(APP_TMP102_I2C_PERIPH_HANDLE);
  uint8_t pr = 0;

  vBSP430platformInitialize_ni();
  (void)iBSP430consoleInitialize();

  cprintf("I2C interface on %s is %p\n", xBSP430serialName(APP_TMP102_I2C_PERIPH_HANDLE), i2c);
#if BSP430_PLATFORM_PERIPHERAL_HELP
  cprintf("TMP102 I2C Pins: %s\n", xBSP430platformPeripheralHelp(APP_TMP102_I2C_PERIPH_HANDLE, BSP430_PERIPHCFG_SERIAL_I2C));
#endif /* BSP430_PLATFORM_PERIPHERAL_HELP */
  i2c = hBSP430serialOpenI2C(i2c,
                             BSP430_SERIAL_ADJUST_CTL0_INITIALIZER(UCMST),
                             0, 0);
  if (! i2c) {
    cprintf("I2C open failed.\n");
    return;
  }

  (void)iBSP430i2cSetAddresses_ni(i2c, -1, APP_TMP102_I2C_ADDRESS);

  /** Raw number is a 16 bit value.  First 12 bits represent the
   * temperature as a count of 0.0625C values.  (If the LSB is 1, then
   * an extended temperature is used and the 13th bit represents a
   * half count.)  0.625 = 5/8; shifting by 3 gets us the 13-bit
   * value; dividing by 2 accounts for the half-count in extended
   * temperature mode. */
#define TMP102_RAW_TO_dC_(raw_) (5 * ((raw_) >> 3) / 16)
#define TMP102_RAW_TO_dC(raw_) ((0 <= (int)(raw_)) ? TMP102_RAW_TO_dC_(raw_) : -TMP102_RAW_TO_dC_(-(int)(raw_)))
#define dC_TO_dF(dC_) (320 + 9 * (dC_) / 5)

#if 0
  {
    unsigned int data[] = { 0x7FF0, 0x4B00, 0x1900, 0xFFC0, 0xE700, 0xC908 };
    int i;

    for (i = 0; i < sizeof(data)/sizeof(*data); ++i) {
      int temp_dC = TMP102_RAW_TO_dC(data[i]);
      cprintf("temp 0x%04x = %d dC = %d d[degF]\n", data[i], temp_dC, dC_TO_dF(temp_dC));
    }
  }
#endif

  while (1) {
    int rc;
    uint8_t data[2];
    uint16_t raw;

    rc = iBSP430i2cTxData_ni(i2c, &pr, 1);
    if (0 > rc) {
      cprintf("I2C TX ERROR\n");
      break;
    }
    memset(data, 0, sizeof(data));
    rc = iBSP430i2cRxData_ni(i2c, data, sizeof(data));
    if (0 > rc) {
      cprintf("I2C RX ERROR\n");
      break;
    }
    raw = data[1] | (data[0] << 8);
    if (0 == pr) {
      int temp_dC = TMP102_RAW_TO_dC(raw);
      cprintf("temp 0x%04x = %d dC = %d d[degF]\n", raw, temp_dC, dC_TO_dF(temp_dC));
    } else {
      cprintf("reg %d is 0x%04x\n", pr, raw);
    }
    pr = (pr + 1) & 0x03;
    BSP430_CORE_DELAY_CYCLES(BSP430_CLOCK_NOMINAL_MCLK_HZ);
  }
}
Exemplo n.º 22
0
void main ()
{
#if (BSP430_CONSOLE - 0)
  const char * help;
  unsigned long smclk_Hz;
  unsigned long aclk_Hz;
#endif /* BSP430_CONSOLE */

  /* First thing you do in main is configure the platform. */
  vBSP430platformInitialize_ni();

  /* If we support a console, dump out a bunch of configuration
   * information. */
#if (BSP430_CONSOLE - 0)
  (void)iBSP430consoleInitialize();
  cputtext("\nclocks " __DATE__ " " __TIME__ "\n");
  cputtext("\nBSP430_PLATFORM_BOOT_CONFIGURE_LFXT1: ");
  cputu(BSP430_PLATFORM_BOOT_CONFIGURE_LFXT1, 10);
  cputtext("\nBSP430_CLOCK_LFXT1_STABILIZATION_DELAY_CYCLES: ");
  cputul(BSP430_CLOCK_LFXT1_STABILIZATION_DELAY_CYCLES, 10);
  cputtext("\nBSP430_PLATFORM_BOOT_LFXT1_DELAY_SEC: ");
  cputu(BSP430_PLATFORM_BOOT_LFXT1_DELAY_SEC, 10);
  cputtext("\nBSP430_PLATFORM_BOOT_CONFIGURE_CLOCKS: ");
  cputu(BSP430_PLATFORM_BOOT_CONFIGURE_CLOCKS, 10);
#if defined(__MSP430_HAS_BC2__)
#if (configBSP430_BC2_TRIM_TO_MCLK - 0)
  cputtext("\nconfigBSP430_BC2_TRIM_TO_MCLK: 1");
#else /* configBSP430_BC2_TRIM_TO_MCLK */
  cputtext("\nconfigBSP430_BC2_TRIM_TO_MCLK: 0");
#endif /* configBSP430_BC2_TRIM_TO_MCLK */
#if (BSP430_BC2_TRIM_TO_MCLK - 0)
  cputtext("\nBSP430_BC2_TRIM_TO_MCLK: 1");
#else /* BSP430_BC2_TRIM_TO_MCLK */
  cputtext("\nBSP430_BC2_TRIM_TO_MCLK: 0");
#endif /* BSP430_BC2_TRIM_TO_MCLK */
#endif /* BC2 */
#if defined(__MSP430_HAS_UCS__) || defined(__MSP430_HAS_UCS_RF__)
#if (configBSP430_UCS_TRIM_DCOCLKDIV - 0)
  cputtext("\nconfigBSP430_UCS_TRIM_DCOCLKDIV: 1");
#else /* configBSP430_UCS_TRIM_DCOCLKDIV */
  cputtext("\nconfigBSP430_UCS_TRIM_DCOCLKDIV: 0");
#endif /* configBSP430_UCS_TRIM_DCOCLKDIV */
#if (BSP430_UCS_TRIM_DCOCLKDIV - 0)
  cputtext("\nBSP430_UCS_TRIM_DCOCLKDIV: 1");
#else /* BSP430_UCS_TRIM_DCOCLKDIV */
  cputtext("\nBSP430_UCS_TRIM_DCOCLKDIV: 0");
#endif /* BSP430_UCS_TRIM_DCOCLKDIV */
#endif /* UCS */

  cputtext("\nBSP430_CLOCK_PUC_MCLK_HZ: ");
  cputul(BSP430_CLOCK_PUC_MCLK_HZ, 10);
  cputtext("\nBSP430_CLOCK_NOMINAL_MCLK_HZ: ");
  cputul(BSP430_CLOCK_NOMINAL_MCLK_HZ, 10);
  cputtext("\nBSP430_CLOCK_LFXT1_IS_FAULTED_NI(): ");
  cputu(BSP430_CLOCK_LFXT1_IS_FAULTED_NI(), 10);
  cputtext("\nBSP430_CLOCK_NOMINAL_VLOCLK_HZ: ");
  cputu(BSP430_CLOCK_NOMINAL_VLOCLK_HZ, 10);
  cputtext("\nBSP430_CLOCK_NOMINAL_XT1CLK_HZ: ");
  cputul(BSP430_CLOCK_NOMINAL_XT1CLK_HZ, 10);
#if defined(BSP430_CLOCK_NOMINAL_XT2CLK_HZ)
  cputtext("\nBSP430_PLATFORM_BOOT_CONFIGURE_XT2: ");
  cputu(BSP430_PLATFORM_BOOT_CONFIGURE_XT2, 10);
  cputtext("\nBSP430_CLOCK_XT2_IS_FAULTED_NI(): ");
  cputu(BSP430_CLOCK_XT2_IS_FAULTED_NI(), 10);
  cputtext("\nBSP430_CLOCK_NOMINAL_XT2CLK_HZ: ");
  cputul(BSP430_CLOCK_NOMINAL_XT2CLK_HZ, 10);
#endif /* BSP430_CLOCK_NOMINAL_XT2CLK_HZ */
  cputtext("\nulBSP430clockMCLK_Hz_ni(): ");
  cputul(ulBSP430clockMCLK_Hz_ni(), 10);
  cputtext("\nBSP430_PLATFORM_BOOT_SMCLK_DIVIDING_SHIFT: ");
  cputi(BSP430_PLATFORM_BOOT_SMCLK_DIVIDING_SHIFT, 10);
  cputtext("\nulBSP430clockSMCLK_Hz_ni(): ");
  smclk_Hz = ulBSP430clockSMCLK_Hz_ni();
  cputul(smclk_Hz, 10);
  cputtext("\nBSP430_PLATFORM_BOOT_ACLK_DIVIDING_SHIFT: ");
  cputi(BSP430_PLATFORM_BOOT_ACLK_DIVIDING_SHIFT, 10);
  cputtext("\nulBSP430clockACLK_Hz_ni(): ");
  aclk_Hz = ulBSP430clockACLK_Hz_ni();
  cputul(aclk_Hz, 10);

#if (BSP430_TIMER_CCACLK - 0)
  if (1000000UL <= aclk_Hz) {
    cputtext("\nUnable to use high-speed ACLK for differential timing of SMCLK");
  } else {
    do {
      const unsigned int SAMPLE_PERIOD_ACLK = 10;
      volatile sBSP430hplTIMER * tp = xBSP430hplLookupTIMER(BSP430_TIMER_CCACLK_PERIPH_HANDLE);
      unsigned int cc_delta;
      unsigned long aclk_rel_smclk_Hz;
      unsigned long smclk_rel_aclk_Hz;

      if (! tp) {
        cputtext("\nUnable to access configured CCACLK timer");
        break;
      }
      /* Capture the SMCLK ticks between adjacent ACLK ticks */
      tp->ctl = TASSEL_2 | MC_2 | TACLR;
      cc_delta = uiBSP430timerCaptureDelta_ni(BSP430_TIMER_CCACLK_PERIPH_HANDLE,
                                              BSP430_TIMER_CCACLK_ACLK_CCIDX,
                                              CM_2,
                                              BSP430_TIMER_CCACLK_ACLK_CCIS,
                                              SAMPLE_PERIOD_ACLK);
      tp->ctl = 0;
      if (-1 == cc_delta) {
        cputtext("\nCCACLK measurement failed");
        break;
      }
      cputchar('\n');
      cputu(SAMPLE_PERIOD_ACLK, 10);
      cputtext(" ticks of ACLK produced ");
      cputu(cc_delta, 10);
      cputtext(" ticks of SMCLK");
      cputtext("\nComparison with measured values:");
      cputtext("\n SMCLK (Hz) (if measured ACLK correct): ");
      smclk_rel_aclk_Hz = (cc_delta * aclk_Hz) / SAMPLE_PERIOD_ACLK;
      cputul(smclk_rel_aclk_Hz, 10);
      cputtext(" (error ");
      cputl(smclk_rel_aclk_Hz - smclk_Hz, 10);
      cputtext(" = ");
      cputl(1000 * labs(smclk_rel_aclk_Hz - smclk_Hz) / smclk_Hz, 10);
      cputtext(" kHz/MHz)");
      cputtext("\n ACLK (Hz) (if measured SMCLK correct): ");
      aclk_rel_smclk_Hz = SAMPLE_PERIOD_ACLK * smclk_Hz / cc_delta;
      cputul(aclk_rel_smclk_Hz, 10);
      cputtext(" (error ");
      cputl(aclk_rel_smclk_Hz - aclk_Hz, 10);
      cputtext(" = ");
      cputl(1000 * labs(aclk_rel_smclk_Hz - aclk_Hz) / aclk_Hz, 10);
      cputtext(" Hz/kHz)");
    } while (0);
  }
#else /* BSP430_TIMER_CCACLK */
  cputtext("\nNo CCACLK timer available for ACLK/SMCLK comparison");
#endif /* BSP430_TIMER_CCACLK */

  cputchar('\n');

#if defined(__MSP430_HAS_BC2__)
  cputtext("\nBC2: DCO ");
  cputu(DCOCTL, 16);
  cputtext(" CTL1  ");
  cputu(BCSCTL1, 16);
  cputtext(" CTL2  ");
  cputu(BCSCTL2, 16);
  cputtext(" CTL3  ");
  cputu(BCSCTL3, 16);

#endif

#if defined(__MSP430_HAS_FLL__) || defined(__MSP430_HAS_FLLPLUS__)
  cprintf("\nFLL: SCF QCTL %02x I0 %02x I1 %02x ; CTL0 %02x CTL1 %02x CTL2 %02x\n",
          SCFQCTL, SCFI0, SCFI1, FLL_CTL0, FLL_CTL1,
#if defined(FLL_CTL2_)
          FLL_CTL2
#else /* FLL_CTL2 */
          ~0
#endif /* FLL_CTL2 */
         );
#endif /* FLL/PLUS */

#if defined(__MSP430_HAS_UCS__) || defined(__MSP430_HAS_UCS_RF__)
  cputtext("\nBSP430_UCS_FLL_SELREF: "
#if SELREF__XT2CLK <= BSP430_UCS_FLL_SELREF
           "XT2CLK"
#elif SELREF__REFOCLK <= BSP430_UCS_FLL_SELREF
           "REFOCLK"
#else /* BSP430_UCS_FLL_SELREF */
           "XT1CLK"
#endif /* BSP430_UCS_FLL_SELREF */
          );
  cprintf("\nUCS RSEL %d DCO %d MOD %d:"
          "\n CTL0 %04x CTL1 %04x CTL2 %04x CTL3 %04x"
          "\n CTL4 %04x CTL5 %04x CTL6 %04x CTL7 %04x",
          0x1F & (UCSCTL1 / DCORSEL0), 0x1F & (UCSCTL0 / DCO0), 0x1F & (UCSCTL0 / MOD0),
          UCSCTL0, UCSCTL1, UCSCTL2, UCSCTL3,
          UCSCTL4, UCSCTL5, UCSCTL6, UCSCTL7);
#endif /* UCS */

#if defined(__MSP430_HAS_CS__) || defined(__MSP430_HAS_CS_A__)
  cprintf("\nCS %s : RSEL %d DCOFSEL %d:"
          "\n CTL0 %04x CTL1 %04x CTL2 %04x CTL3 %04x"
          "\n CTL4 %04x CTL5 %04x CTL6 %04x"
          "\n FRCTL0 %04x",
#if (BSP430_CS_IS_FR57XX - 0)
          "FR57xx"
#endif
#if (BSP430_CS_IS_FR58XX - 0)
          "FR58xx"
#endif
          "", !!(DCORSEL & CSCTL1), 0x07 & (CSCTL1 / DCOFSEL0),
          CSCTL0, CSCTL1, CSCTL2, CSCTL3,
          CSCTL4, CSCTL5, CSCTL6, FRCTL0);
#endif /* CS */

#endif /* BSP430_CONSOLE */

  if (0 == iBSP430platformConfigurePeripheralPins_ni(BSP430_PERIPH_EXPOSED_CLOCKS, 0, 1)) {
#if (BSP430_CONSOLE - 0)
    cputtext("\n\nClock signals exposed:\n ");
    help = NULL;
#ifdef BSP430_PLATFORM_PERIPHERAL_HELP
    help = xBSP430platformPeripheralHelp(BSP430_PERIPH_EXPOSED_CLOCKS, 0);
#endif /* BSP430_PLATFORM_PERIPHERAL_HELP */
    if (NULL == help) {
      help = "Go look at the data sheet and source, because nobody told me where they are";
    }
    cputtext(help);
    cputtext("\nStatus register LPM bits: ");
    cputu(__read_status_register() & BSP430_CORE_LPM_SR_MASK, 16);
    cputtext("\nIFG1 bits: ");
#if defined(__MSP430_HAS_MSP430XV2_CPU__)
    cputu(SFRIFG1, 16);
#else /* CPUX */
    cputu(IFG1, 16);
#endif /* CPUX */
    cputtext(" with OFIFG ");
    cputu(OFIFG, 16);
    cputchar('\n');
#endif /* BSP430_CONSOLE */

    /* Spin here with CPU active.  In LPM0, MCLK is disabled.  Other
     * clocks get disabled at deeper sleep modes; if you fall off the
     * bottom, you might end up in LPM4 with all clocks disabled. */
    while (1) {
      vBSP430ledSet(0, -1);
      BSP430_CORE_WATCHDOG_CLEAR();
      BSP430_CORE_DELAY_CYCLES(BSP430_CLOCK_NOMINAL_MCLK_HZ / 2);
    }
  } else {
#if (BSP430_CONSOLE - 0)
    cputtext("\nFailed to expose clock signals\n");
#endif /* BSP430_CONSOLE */
  }
}
Exemplo n.º 23
0
void main (void)
{
  unsigned long wake_utt;
  int rc;
  long lrc;
  char as_text[BSP430_UPTIME_AS_TEXT_LENGTH];
  uint32_u ntp_addr;
  uint32_u self_addr;

  vBSP430platformInitialize_ni();
  (void)iBSP430consoleInitialize();
  cprintf("\nntp " __DATE__ " " __TIME__ "\n");

  /* Initialization can be done with interrupts disabled, since the
   * function does nothing but store callbacks.  We use the same
   * callback for all three update capabilities. */
  rc = iBSP430cc3000spiInitialize(wlan_cb, NULL, NULL, NULL);
  if (0 > rc) {
    cprintf("ERR: Initialization failed: %d\n", rc);
    return;
  }

  BSP430_CORE_ENABLE_INTERRUPT();

  /* Local addresses use all zeros for inet addr.  bind does not
   * support dynamic assignment of unused port through sin_port=0. */
  memset(&local_addr, 0, sizeof(local_addr));
  local_addr.sai.sin_family = AF_INET;
  local_addr.sai.sin_port = htons(60123);

  /* Remote server will be determined by DNS from the NTP pool once we
   * start. */
  remote_addr = local_addr;
  remote_addr.sai.sin_port = htons(123);

  ntp_addr.u32 = 0;
  self_addr.u32 = 0;

  cprintf("Remote: %s:%u\n", net_ipv4AsText(&remote_addr.sai.sin_addr), ntohs(remote_addr.sai.sin_port));
  rc = sizeof(sBSP430uptimeNTPPacketHeader);
  if (48 != rc) {
    cprintf("ERR: NTP header size %d\n", rc);
    return;
  }
  wake_utt = ulBSP430uptime();

  (void)rc;
  while (1) {
    unsigned long timeout_utt;

    do {
      tNetappIpconfigRetArgs ipc;
      unsigned long start_utt;
      unsigned long finished_utt;
      int sfd;
      int nfds;
      fd_set rfds;
      int servers_left;
      int retries_left;

      /* Clear everything as we're starting a cycle */
      BSP430_CORE_DISABLE_INTERRUPT();
      do {
        event_flags_v = 0;
        start_utt = ulBSP430uptime_ni();
      } while (0);
      BSP430_CORE_ENABLE_INTERRUPT();

      /* Start the WAN process.  This is asynchronous; wait up to 2
       * seconds for it to complete. */
      cprintf("%s: ", xBSP430uptimeAsText(start_utt, as_text));
      cputchar('W');
      wlan_start(0);
      vBSP430ledSet(BSP430_LED_RED, 1);
      (void)wlan_set_event_mask(0UL);
      lrc = BSP430_UPTIME_MS_TO_UTT(2000);
      timeout_utt = ulBSP430uptime() + lrc;
      while ((! (EVENT_FLAG_WLANCONN & event_flags_v))
             && (0 < ((lrc = lBSP430uptimeSleepUntil(timeout_utt, LPM0_bits))))) {
      }
      if (! (EVENT_FLAG_WLANCONN & event_flags_v)) {
        cprintf("WLAN start failed\n");
        break;
      }

      /* Wait for IP connectivity (signalled by a DHCP event).
       * Continue using the previous timeout. */
      cputchar('D');
      while ((! (EVENT_FLAG_IPCONN & event_flags_v))
             && (0 < ((lrc = lBSP430uptimeSleepUntil(timeout_utt, LPM0_bits))))) {
      }
      if (! (EVENT_FLAG_IPCONN & event_flags_v)) {
        cprintf("IP conn failed\n");
        break;
      }

      /* Inspect the IP configuration.  Sometimes we get the event,
       * but there's no IP assigned. */
      netapp_ipconfig(&ipc);
      memcpy(self_addr.u8, ipc.aucIP, sizeof(self_addr));
      if (! self_addr.u32) {
        cprintf("IP assignment failed\n");
        break;
      }
      vBSP430ledSet(BSP430_LED_GREEN, 1);

      /* Obtain a UDP socket and bind it for local operations. */
      cputchar('I');
      sfd = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
      if (0 > sfd) {
        cprintf("socket() failed: %d\n", sfd);
        break;
      }
      cputchar('S');
      lrc = bind(sfd, &local_addr.sa, sizeof(local_addr.sa));
      if (0 > lrc) {
        cprintf("bind() failed: %ld\n", lrc);
        break;
      }
      cputchar('B');

      servers_left = NTP_SERVERS_PER_ATTEMPT;
      retries_left = NTP_REQUESTS_PER_SERVER;
      do {
        sBSP430uptimeNTPPacketHeader ntp0;
        sBSP430uptimeNTPPacketHeader ntp1;
        int have_invalid_epoch;
        struct timeval tv;
        sockaddr_u src;
        socklen_t slen = sizeof(src);
        unsigned long recv_utt;
        uint64_t recv_ntp;
        int64_t adjustment_ntp;
        long adjustment_ms;
        unsigned long rtt_us;

        have_invalid_epoch = 0 != iBSP430uptimeCheckEpochValidity();
        if (! remote_addr.sai.sin_addr.s_addr) {
          const char ntp_fqdn[] = "0.pool.ntp.org";
          ntp_addr.u32 = 0;
          rc = gethostbyname((char *)ntp_fqdn, sizeof(ntp_fqdn)-1, &ntp_addr.u32);
          cputchar('d');
          if (-95 == rc) { /* ARP request failed; retry usually works */
            rc = gethostbyname((char *)ntp_fqdn, sizeof(ntp_fqdn)-1, &ntp_addr.u32);
            cputchar('d');
          }
          if (0 == ntp_addr.u32) {
            cprintf("gethostbyname(%s) failed: %d\n", ntp_fqdn, rc);
            rc = -1;
            break;
          }
          remote_addr.sai.sin_addr.s_addr = htonl(ntp_addr.u32);
          cprintf("{%s}", net_ipv4AsText(&remote_addr.sai.sin_addr));
          retries_left = NTP_REQUESTS_PER_SERVER;
        }

        /* Configure the NTP request and send it */
        iBSP430uptimeInitializeNTPRequest(&ntp0);
        iBSP430uptimeSetNTPXmtField(&ntp0, NULL);
        BSP430_CORE_DISABLE_INTERRUPT();
        do {
          /* Clear the shutdown bit, so we know when it's ok to shut
           * down after this send */
          event_flags_v &= ~EVENT_FLAG_SHUTDOWN;
        } while (0);
        BSP430_CORE_ENABLE_INTERRUPT();
        rc = sendto(sfd, &ntp0, sizeof(ntp0), 0, &remote_addr.sa, sizeof(remote_addr.sai));
        if (sizeof(ntp0) != rc) {
          cprintf("sendto %s:%u failed: %d\n", net_ipv4AsText(&remote_addr.sai.sin_addr), ntohs(remote_addr.sai.sin_port), rc);
          rc = -1;
          break;
        }
        cputchar('s');

        /* If we get an answer it should be here in less than 100
         * ms, but give it 400 ms just to be kind. */
        tv.tv_sec = 0;
        tv.tv_usec = 400000UL;
        FD_ZERO(&rfds);
        FD_SET(sfd, &rfds);
        nfds = sfd+1;
        rc = select(nfds, &rfds, NULL, NULL, &tv);
        if (! FD_ISSET(sfd, &rfds)) {
          /* We didn't get an answer.  If there are any retries left, use them. */
          if (0 < retries_left--) {
            rc = 1;
            continue;
          }
          /* No retries left on this server: forget about it.  If
           * there are any servers left, try another. */
          cputchar('!');
          remote_addr.sai.sin_addr.s_addr = 0;
          if (0 < servers_left--) {
            rc = 1;
            continue;
          }
          /* No retries from all available servers.  Fail this attempt */
          cprintf("no responsive NTP server found\n");
          rc = -1;
          break;
        }

        /* Got a response.  Record the time it came in and then read
         * it (no high-resolution packet RX time available, but we
         * believe it's here already so set the RX time first).  The
         * message is unacceptable if it isn't an NTP packet. */
        recv_utt = ulBSP430uptime();
        rc = recvfrom(sfd, &ntp1, sizeof(ntp1), 0, &src.sa, &slen);
        if (sizeof(ntp1) != rc) {
          cprintf("recv failed: %d\n", rc);
          rc = -1;
          break;
        }
        cputchar('r');

        /* Convert the RX time to NTP, then process the message to
         * determine the offset. */
        rc = iBSP430uptimeAsNTP(recv_utt, &recv_ntp, have_invalid_epoch);
        if (0 != rc) {
          cprintf("NTP decode failed: %d\n", rc);
          continue;
        }
        rc = iBSP430uptimeProcessNTPResponse(&ntp0, &ntp1, recv_ntp, &adjustment_ntp, &adjustment_ms, &rtt_us);
        if (0 != rc) {
          cprintf("Process failed: %d\n", rc);
          continue;
        }
        if (have_invalid_epoch) {
          rc = iBSP430uptimeSetEpochFromNTP(BSP430_UPTIME_BYPASS_EPOCH_NTP + adjustment_ntp);
          cputchar('E');
          if (0 != rc) {
            cprintf("\nERR: SetEpoch failed: %d\n", rc);
          }
#if (NTP_ADJUST_EACH_ITER - 0)
        } else {
          rc = iBSP430uptimeAdjustEpochFromNTP(adjustment_ntp);
          cputchar('A');
          if (0 != rc) {
            cprintf("\nERR: AdjustEpoch failed: %d\n", rc);
          }
#endif
        }
        cprintf("[%s:%u adj %lld ntp = %ld ms, rtt %lu us]",
                net_ipv4AsText(&remote_addr.sai.sin_addr), ntohs(remote_addr.sai.sin_port),
                adjustment_ntp, adjustment_ms, rtt_us);
      } while (0 != rc);
      if (0 != rc) {
        cprintf("NTP query failed\n");
        break;
      }
#if 0
      /* The shutdown OK seems to arrive about 1000 ms after the last
       * transmit, which is unnecessarily long.  As we're not doing
       * TCP, there's no reason to wait for it. */
      lrc = BSP430_UPTIME_MS_TO_UTT(4000);
      timeout_utt = ulBSP430uptime() + lrc;
      while ((! (EVENT_FLAG_SHUTDOWN & event_flags_v))
             && (0 < ((lrc = lBSP430uptimeSleepUntil(timeout_utt, LPM0_bits))))) {
      }
      if (! (EVENT_FLAG_SHUTDOWN & event_flags_v)) {
        cprintf("SHUTDOWN ok never received\n");
        break;
      }
#endif
      finished_utt = ulBSP430uptime();
      cprintf("[%s]\n", xBSP430uptimeAsText(finished_utt - start_utt, as_text));
    } while (0);

    BSP430_CORE_DISABLE_INTERRUPT();
    do {
      event_flags_v = 0;
    } while (0);
    BSP430_CORE_ENABLE_INTERRUPT();
    wlan_stop();
    vBSP430ledSet(BSP430_LED_GREEN, 0);
    vBSP430ledSet(BSP430_LED_RED, 0);
    wake_utt += 60 * ulBSP430uptimeConversionFrequency_Hz();
    while (0 < lBSP430uptimeSleepUntil(wake_utt, LPM2_bits)) {
    }
  }
  cprintf("Fell off end\n");
}