Example #1
0
static int cmd_test(int argc, char **argv)
{
    int page;
    char fill = 'a';

    if (argc < 2) {
        printf("usage: %s <page>\n", argv[0]);
        return 1;
    }

    page = getpage(argv[1]);
    if (page < 0) {
        return 1;
    }

    for (unsigned i = 0; i < sizeof(page_mem); i++) {
        page_mem[i] = (uint8_t)fill++;
        if (fill > 'z') {
            fill = 'a';
        }
    }

    if (flashpage_write_and_verify(page, page_mem) != FLASHPAGE_OK) {
        printf("error verifying the content of page %i\n", page);
        return 1;
    }

    printf("wrote local page buffer to flash page %i at addr %p\n",
           page, flashpage_addr(page));
    return 0;
}
Example #2
0
void flashpage_write(int page, void *data)
{
    assert(page < FLASHPAGE_NUMOF);

    uint32_t *page_addr = (uint32_t *)flashpage_addr(page);

    /* remove peripheral access lock for the NVMCTRL peripheral */
#ifdef CPU_FAM_SAML21
    PAC->WRCTRL.reg = (PAC_WRCTRL_KEY_CLR | ID_NVMCTRL);
#else
    if (PAC1->WPSET.reg & NVMCTRL_PAC_BIT) {
        PAC1->WPCLR.reg = NVMCTRL_PAC_BIT;
    }
#endif

    /* erase given page (the ADDR register uses 16-bit addresses) */
    NVMCTRL->ADDR.reg = (((uint32_t)page_addr) >> 1);
    NVMCTRL->CTRLA.reg = (NVMCTRL_CTRLA_CMDEX_KEY | NVMCTRL_CTRLA_CMD_ER);
    while (!NVMCTRL->INTFLAG.bit.READY) {}

    /* write data to page */
    if (data != NULL) {
        uint32_t *data_addr = (uint32_t *)data;
        NVMCTRL->CTRLA.reg = (NVMCTRL_CTRLA_CMDEX_KEY | NVMCTRL_CTRLA_CMD_PBC);
        for (unsigned i = 0; i < (FLASHPAGE_SIZE / 4); i++) {
            *page_addr++ = data_addr[i];
        }
        NVMCTRL->CTRLA.reg = (NVMCTRL_CTRLA_CMDEX_KEY | NVMCTRL_CTRLA_CMD_WP);
    }
}
Example #3
0
int flashpage_verify(int page, void *data)
{
    assert(page < (int)FLASHPAGE_NUMOF);

    if (memcmp(flashpage_addr(page), data, FLASHPAGE_SIZE) == 0) {
        return FLASHPAGE_OK;
    }
    else {
        return FLASHPAGE_NOMATCH;
    }
}
Example #4
0
File: main.c Project: OTAkeys/RIOT
/**
 * @brief   Does a short raw write on last page available
 *
 * @note    Since every hardware can have different flash layouts for
 *          automated testing we always write to the last page available
 *          so we are independent of the size or layout
 */
static int cmd_test_last_raw(int argc, char **argv)
{
    (void) argc;
    (void) argv;

    /* try to align */
    memcpy(raw_buf, "test12344321tset", 16);

    /* erase the page first */
    flashpage_write(((int)FLASHPAGE_NUMOF - 1), NULL);

    flashpage_write_raw(flashpage_addr((int)FLASHPAGE_NUMOF - 1), raw_buf, strlen(raw_buf));

    /* verify that previous write_raw effectively wrote the desired data */
    if (memcmp(flashpage_addr((int)FLASHPAGE_NUMOF - 1), raw_buf, strlen(raw_buf)) != 0) {
        puts("error verifying the content of last page");
        return 1;
    }

    puts("wrote raw short buffer to last flash page");
    return 0;
}
Example #5
0
static int cmd_erase(int argc, char **argv)
{
    int page;

    if (argc < 2) {
        printf("usage: %s <page>\n", argv[0]);
        return 1;
    }

    page = getpage(argv[1]);
    if (page < 0) {
        return 1;
    }
    flashpage_write(page, NULL);

    printf("successfully erased page %i (addr %p)\n",
           page, flashpage_addr(page));
    return 0;
}
Example #6
0
void flashpage_write(int page, const void *data)
{
    assert(page < FLASHPAGE_NUMOF);

    uint32_t *page_addr = (uint32_t *)flashpage_addr(page);

    /* erase given page (the ADDR register uses 16-bit addresses) */
    _unlock();
    NVMCTRL->ADDR.reg = (((uint32_t)page_addr) >> 1);
    NVMCTRL->CTRLA.reg = (NVMCTRL_CTRLA_CMDEX_KEY | NVMCTRL_CTRLA_CMD_ER);
    while (!NVMCTRL->INTFLAG.bit.READY) {}
    _lock();

    /* write data to page */
    if (data != NULL) {
        flashpage_write_raw(page_addr, data, FLASHPAGE_SIZE);
    }

}
Example #7
0
static int cmd_dump(int argc, char **argv)
{
    int page;
    void *addr;

    if (argc < 2) {
        printf("usage: %s <page>\n", argv[0]);
        return 1;
    }

    page = getpage(argv[1]);
    if (page < 0) {
        return 1;
    }
    addr = flashpage_addr(page);

    printf("Flash page %i at address %p\n", page, addr);
    memdump(addr, FLASHPAGE_SIZE);

    return 0;
}
Example #8
0
static int cmd_write(int argc, char **argv)
{
    int page;

    if (argc < 2) {
        printf("usage: %s <page>\n", argv[0]);
        return 1;
    }

    page = getpage(argv[1]);
    if (page < 0) {
        return 1;
    }

    if (flashpage_write_and_verify(page, page_mem) != FLASHPAGE_OK) {
        printf("error: verification for page %i failed\n", page);
        return 1;
    }

    printf("wrote local page buffer to flash page %i at addr %p\n",
           page, flashpage_addr(page));
    return 0;
}
Example #9
0
void flashpage_write(int page, void *data)
{
    assert(page < FLASHPAGE_NUMOF);

    uint32_t *page_addr = (uint32_t *)flashpage_addr(page);
    uint32_t *data_addr = (uint32_t *)data;

    /* erase given page */
    NRF_NVMC->CONFIG = NVMC_CONFIG_WEN_Een;
    NRF_NVMC->ERASEPAGE = (uint32_t)page_addr;
    while (NRF_NVMC->READY == 0) {}

    /* write data to page */
    if (data != NULL) {
        NRF_NVMC->CONFIG = NVMC_CONFIG_WEN_Wen;
        for (unsigned i = 0; i < (FLASHPAGE_SIZE / 4); i++) {
            *page_addr++ = data_addr[i];
        }
    }

    /* finish up */
    NRF_NVMC->CONFIG = NVMC_CONFIG_WEN_Ren;
}
Example #10
0
void flashpage_read(int page, void *data)
{
    assert(page < (int)FLASHPAGE_NUMOF);

    memcpy(data, flashpage_addr(page), FLASHPAGE_SIZE);
}
Example #11
0
void flashpage_write(int page, void *data)
{
    assert(page < FLASHPAGE_NUMOF);

    uint16_t *page_addr = flashpage_addr(page);
    uint16_t *data_addr = (uint16_t *)data;
    uint32_t hsi_state = (RCC->CR & RCC_CR_HSION);

    /* the internal RC oscillator (HSI) must be enabled */
    RCC->CR |= (RCC_CR_HSION);
    while (!(RCC->CR & RCC_CR_HSIRDY)) {}

    /* unlock the flash module */
    DEBUG("[flashpage] unlocking the flash module\n");
    if (FLASH->CR & FLASH_CR_LOCK) {
        FLASH->KEYR = FLASH_KEY1;
        FLASH->KEYR = FLASH_KEY2;
    }

    /* ERASE sequence */
    /* make sure no flash operation is ongoing */
    DEBUG("[flashpage] erase: waiting for any operation to finish\n");
    while (FLASH->SR & FLASH_SR_BSY) {}
    /* set page erase bit and program page address */
    DEBUG("[flashpage] erase: setting the erase bit and page address\n");
    FLASH->CR |= FLASH_CR_PER;
    FLASH->AR = (uint32_t)flashpage_addr(page);
    DEBUG("address to erase: %p\n", flashpage_addr(page));
    /* trigger the page erase and wait for it to be finished */
    DEBUG("[flashpage] erase: trigger the page erase\n");
    FLASH->CR |= FLASH_CR_STRT;
    DEBUG("[flashpage] erase: wait as long as device is busy\n");
    while (FLASH->SR & FLASH_SR_BSY) {}
    /* reset PER bit */
    DEBUG("[flashpage] erase: resetting the page erase bit\n");
    FLASH->CR &= ~(FLASH_CR_PER);

    /* WRITE sequence */
    if (data != NULL) {
        DEBUG("[flashpage] write: now writing the data\n");
        /* set PG bit and program page to flash */
        FLASH->CR |= FLASH_CR_PG;
        for (unsigned i = 0; i < (FLASHPAGE_SIZE / 2); i++) {
            *page_addr++ = data_addr[i];
            while (FLASH->SR & FLASH_SR_BSY) {}
        }
        /* clear program bit again */
        FLASH->CR &= ~(FLASH_CR_PG);
        DEBUG("[flashpage] write: done writing data\n");
    }

    /* finally, lock the flash module again */
    DEBUG("flashpage] now locking the flash module again\n");
    FLASH->CR |= FLASH_CR_LOCK;

    /* restore the HSI state */
    if (!hsi_state) {
        RCC->CR &= ~(RCC_CR_HSION);
        while (RCC->CR & RCC_CR_HSIRDY) {}
    }
}