bool WiFiMDNSResponder::parseRequest() { int packetLength = udpSocket.parsePacket(); if (packetLength) { // check if parsed packet matches expected request length if (packetLength < minimumExpectedRequestLength) { // it does not, read the full packet in and drop data while(udpSocket.available()) { udpSocket.read(); } return false; } // read up to the min expect request length uint8_t request[minimumExpectedRequestLength]; udpSocket.read(request, minimumExpectedRequestLength); // discard the rest while(udpSocket.available()) { udpSocket.read(); } // parse request uint8_t requestNameLength = request[HEADER_SIZE]; uint8_t* requestName = &request[HEADER_SIZE + 1]; uint8_t requestDomainLength = request[HEADER_SIZE + 1 + requestNameLength]; uint8_t* requestDomain = &request[HEADER_SIZE + 1 + requestNameLength + 1]; uint16_t requestQtype; uint16_t requestQclass; memcpy(&requestQtype, &request[minimumExpectedRequestLength - 4], sizeof(requestQtype)); memcpy(&requestQclass, &request[minimumExpectedRequestLength - 2], sizeof(requestQclass)); requestQtype = _ntohs(requestQtype); requestQclass = _ntohs(requestQclass); // compare request if (memcmp_P(request, expectedRequestHeader, 4) == 0 && // request header start match memcmp_P(&request[6], &expectedRequestHeader[6], 6) == 0 && // request header end match requestNameLength == name.length() && // name length match strncasecmp(name.c_str(), (char*)requestName, requestNameLength) == 0 && // name match requestDomainLength == sizeof(domain) && // domain length match memcmp_P(requestDomain, domain, requestDomainLength) == 0 && // suffix match requestQtype == 0x0001 && // request QType match requestQclass == 0x0001) { // request QClass match return true; } } return false; }
// Open a WAV file, parse the chunks, and prepare to start reading audio data // Returns 0 if failure, 1 if successful. // NOTE: It uses one of the global ping-pong buffers for temporary storage uint8_t wav_open(const char *fname) { FRESULT fresult; UINT bytesRead; uint32_t lChunkSize; uint8_t *buf = (uint8_t *)gBuffers; (void) fail_major(FAIL_WAV_OPEN); fresult = f_open(&gFile, fname, FA_READ | FA_OPEN_EXISTING); if (fresult != FR_OK) return fail_minor(FAIL_WAV_NO_FILE); fresult = f_read(&gFile, buf, 36, &bytesRead); if ((fresult != FR_OK) || (bytesRead<36)) return fail_minor(FAIL_WAV_NO_HEADER); // First 4 bytes: RIFF if (memcmp_P(buf, PSTR("RIFF"), 4)) return fail_minor(FAIL_WAV_NO_RIFF); // Bytes 4-7: size of remaining data, hence file size is this plus previous 8 bytes //gWAVInfo.mFileSize = *(uint32_t *)(buf+4) + 8; // Bytes 8-11: WAVE if (memcmp_P(buf+8, PSTR("WAVE"), 4)) return fail_minor(FAIL_WAV_NO_WAVE); // Bytes 12-15: "fmt " if (memcmp_P(buf+12, PSTR("fmt "), 4)) return fail_minor(FAIL_WAV_NO_FMT); // Bytes 16-19: fmt chunk size (should be 16 for PCM) lChunkSize = *(uint32_t *)(buf+16); if (lChunkSize < 16) return fail_minor(FAIL_WAV_BAD_FMT); // Bytes 20-21: audio format, should be 1 for PCM, something else for compression if (*(uint16_t *)(buf+20) != 1) return fail_minor(FAIL_WAV_NOT_PCM); // Bytes 22-36: number of channels, sample rate, byte rate, block alignment, bits per sample memcpy(& (gWAVInfo.mChannels), buf+22, 14); // If chunk size is not 16, skip to the end of the chunk //if (lChunkSize > 16) { f_lseek(&gFile, f_tell(&gFile) + (lChunkSize-16)); //} // Now read data chunk fresult = f_read(&gFile, buf, 8, &bytesRead); if ((fresult != FR_OK) || (bytesRead<8)) return fail_minor(FAIL_WAV_NO_DATA); if (memcmp_P(buf, PSTR("data"), 4)) return fail_minor(FAIL_WAV_BAD_DATA); gChunkBytesRemaining = *(uint32_t *)(buf+4); return fail_nofail(); }
/* The expected return value must be (dst + expret) in case of expret >= 0, or NULL in case of expret == -1. */ static void Check (int line, const void *src , int val, size_t len, /* memccpy() args */ int expret, /* expecter return */ const void *expdst, size_t explen) /* expected result */ { char tsrc[len]; char tdst[len]; char *p; memcpy_P (tsrc, src, len); p = memccpy (tdst, tsrc, val, len); if (expret == -1) { if (p) { PRINTFLN (line, "nonzero result, must NULL"); EXIT (1000 + line); } } else { if (!p) { PRINTFLN (line, "result is NULL, must dst+%d", expret); EXIT (2000 + line); } if (p != tdst + expret) { PRINTFLN (line, "result: dst+%d, must: dst+%d", p - tdst, expret); EXIT (3000 + line); } } if (explen) { if (memcmp_P (tdst, expdst, explen)) { PRINTFLN (line, "result string is wrong"); EXIT (4000 + line); } } }
void Check (int line, const void *s1, size_t n1, const char *s2, size_t n2, int expect) { char t1[300]; char *p; if (n1 > sizeof(t1)) exit (1); memcpy_P (t1, s1, n1); p = memmem_P (t1, n1, s2, n2); if (expect < 0) { if (p) { PRINTFLN (line, "return nonzero"); EXIT (line); } } else { if (p != t1 + expect) { PRINTFLN (line, "expect= %d result= %d", expect, p - t1); EXIT (1000 + line); } } if (memcmp_P (t1, s1, n1)) { PRINTFLN (line, "string is changed"); EXIT (2000 + line); } }
void Check (int line, const char *s, int c, size_t len, int expect) { char t[320]; char *p; if (len > sizeof(t)) exit (1); memcpy_P (t, s, len); p = memrchr (t, c, len); if (expect < 0) { if (p) { PRINTFLN (line, "non zero pointer is returned"); EXIT (line); } } else { if (p != t + expect) { PRINTFLN (line, "expect= %d result= %d", expect, p - t); EXIT (line + 1000); } } if (memcmp_P (t, s, len)) { PRINTFLN (line, "string is changed"); EXIT (line + 2000); } }
int main () { /* Zero width. */ #ifdef __AVR__ CHECK (0, (v.s[0] == FILL), "A", "%0c", v.s); #else CHECK (1, (v.s[0] == 'A'), "A", "%0c", v.s); #endif /* Left width digit is 0. */ CHECK (1, (v.s[0] == 'A'), "A", "%01c", v.s); CHECK (1, !memcmp_P(v.s, PSTR("AB"), 2), "AB", "%02c", v.s); /* Invalid symbol after '%'. */ CHECK (0, (v.s[0] == FILL), "A", "% c", v.s); CHECK (0, (v.s[0] == FILL), "A", "%-c", v.s); CHECK (0, (v.s[0] == FILL), "A", "%+c", v.s); CHECK (0, (v.s[0] == FILL), "A", "%.c", v.s); CHECK (0, (v.s[0] == FILL), "A", "%#c", v.s); /* The length modifier. */ CHECK (1, (v.s[0] == 'A' && v.s[1] == FILL), "A", "%hc", v.s); #ifdef __AVR__ CHECK (1, (v.s[0] == 'A' && v.s[1] == FILL), "A", "%lc", v.s); #else CHECK (1, (v.s[0] == 'A' && v.s[1] == 0), "A", "%lc", v.s); #endif return 0; }
int oid_cmpn(ptr_t* req_oid, ptr_t* progmem_oid, u8t len) { #if CONTIKI_TARGET_AVR_RAVEN && ENABLE_PROGMEM return memcmp_P(req_oid->ptr, (PGM_P)pgm_read_word(&progmem_oid->ptr), min(req_oid->len, len)); #else return memcmp(req_oid->ptr, progmem_oid->ptr, min(req_oid->len, len)); #endif }
void rf_ctrl_init(void) { nRF_Init(); // write the addresses nRF_WriteAddrReg(TX_ADDR, DongleAddr, 5); // we need to set the RX address to the same as TX to be // able to receive ACK nRF_WriteAddrReg(RX_ADDR_P0, DongleAddr, 5); #ifdef NRF_CHECK_MODULE nRF_data[1] = 0; nRF_data[2] = 0; nRF_data[3] = 0; nRF_data[4] = 0; nRF_data[5] = 0; nRF_ReadAddrReg(TX_ADDR, 5); // read the address back // compare if (memcmp_P(nRF_data + 1, &DongleAddr, 5) != 0) { //printf("buff=%02x %02x %02x %02x %02x\n", buff[0], buff[1], buff[2], buff[3], buff[4]); //printf("nRF_=%02x %02x %02x %02x %02x\n", nRF_data[1], nRF_data[2], nRF_data[3], nRF_data[4], nRF_data[5]); // toggle the CAPS LED forever //uint8_t c; //for (c = 0; c < 10; ++c) for (;;) { TogBit(PORT(LED_CAPS_PORT), LED_CAPS_BIT); _delay_ms(300); } } #endif // NRF_CHECK_MODULE nRF_WriteReg(EN_AA, vENAA_P0); // enable auto acknowledge nRF_WriteReg(EN_RXADDR, vERX_P0); // enable RX address (for ACK) nRF_WriteReg(SETUP_RETR, vARD_250us // auto retransmit delay - ARD | 0x0f); // auto retransmit count - ARC nRF_WriteReg(FEATURE, vEN_DPL | vEN_ACK_PAY); // enable dynamic payload length and ACK payload nRF_WriteReg(DYNPD, vDPL_P0); // enable dynamic payload length for pipe 0 nRF_FlushRX(); nRF_FlushTX(); nRF_WriteReg(STATUS, vRX_DR | vTX_DS | vMAX_RT); // reset the IRQ flags nRF_WriteReg(RF_CH, CHANNEL_NUM); // set the channel // reset the the lost packet counters plos_total = arc_total = rf_packets_total = 0; }
int main () { /* A few conversions. */ CHECK (2, !memcmp_P(v.c, PSTR("AB\000CD\000"), 6), "ABCD", "%[AB]%[CD]", v.c, v.c + 3); /* Suppress a writing. */ CHECK (0, (v.c[0] == FILL), "A", "%*[A]", v.c); CHECK (2, !memcmp_P(v.c, PSTR("A\000C\000"), 4), "ABC", "%[A]%*[B]%[C]", v.c, v.c + 2); /* Width field. */ CHECK (1, !strcmp_P(v.c, PSTR("A")), "A", "%1[A]", v.c); CHECK (1, !strcmp_P(v.c, PSTR("A")), "ABCD", "%1[A-Z]", v.c); CHECK (1, !strcmp_P(v.c, PSTR("AB")), "ABCD", "%2[A-Z]", v.c); CHECK (2, !memcmp_P(v.c, PSTR("CD\000AB\000"), 6), "ABCD", "%2[A-Z]%2[A-Z]", v.c + 3, v.c); CHECK (1, !strcmp_P(v.c, PSTR("the_quick_b")), "the_quick_brown_fox", "%11[a-z_]", v.c); /* Suppress and width. */ CHECK (0, (v.c[0] == FILL), "A", "%*1[A]", v.c); CHECK (0, (v.c[0] == FILL), "AA", "%*2[A]", v.c); /* Zero width. */ #ifdef __AVR__ CHECK (0, (v.c[0] == FILL && v.c[1] == FILL), "A", "%0[A]", v.c); #else CHECK (1, !strcmp_P(v.c, PSTR("A")), "A", "%0[A]", v.c); /* ??? */ #endif /* Left width digit is 0. */ CHECK (1, !strcmp_P(v.c, PSTR("A")), "ABCD", "%01[A-Z]", v.c); CHECK (1, !strcmp_P(v.c, PSTR("AB")), "ABCD", "%02[A-Z]", v.c); /* Invalid symbol after '%'. */ CHECK (0, (v.c[0] == FILL), "A", "% [A]", v.c); CHECK (0, (v.c[0] == FILL), "A", "%-[A]", v.c); CHECK (0, (v.c[0] == FILL), "A", "%+[A]", v.c); CHECK (0, (v.c[0] == FILL), "A", "%.[A]", v.c); CHECK (0, (v.c[0] == FILL), "A", "%#[A]", v.c); return 0; }
/* internal public functions ================================================ */ int main (void) { vLedInit(); for (;;) { vWIfcInit (); GetMid (ucMid); GetPnCode (ucPnCode); vAssert (memcmp_P (ucPnCode, ucPnCodeDef_P, sizeof(ucPnCodeDef_P)) == 0); SetPnCode_P (ucPnCode_P); GetPnCode (ucPnCode); vAssert (memcmp_P (ucPnCode, ucPnCode_P, sizeof(ucPnCode_P)) == 0); SetPnCode (ucPnCode); vLedToggle (LED_LED1); delay_ms (500); } return 0; }
void quick_test(void){ uint8_t *ciphertext, *plaintext, rc; uint8_t seed[sizeof(SEED)], seed_out[sizeof(SEED)]; uint16_t clen, plen; if(!keys_allocated){ load_fix_rsa(); } ciphertext = malloc(clen = bigint_length_B(&pub_key.modulus)); plaintext = malloc(clen); memcpy_P(plaintext, MSG, sizeof(MSG)); memcpy_P(seed, SEED, sizeof(SEED)); cli_putstr_P(PSTR("\r\nplaintext:")); cli_hexdump_block(plaintext, sizeof(MSG), 4, 16); cli_putstr_P(PSTR("\r\nseed:")); cli_hexdump_block(seed, sizeof(SEED), 4, 16); cli_putstr_P(PSTR("\r\nencrypting: ...")); rc = rsa_encrypt_pkcs1v15(ciphertext, &clen, plaintext, sizeof(MSG), &pub_key, seed); if(rc){ cli_putstr_P(PSTR("\r\nERROR: rsa_encrypt_pkcs1v15 returned: ")); cli_hexdump_byte(rc); return; } cli_putstr_P(PSTR("\r\n\r\nciphertext:")); cli_hexdump_block(ciphertext, clen, 4, 16); if(clen != sizeof(ENCRYPTED)){ cli_putstr_P(PSTR("\r\n>>FAIL (no size match)<<")); return; }else{ if(memcmp_P(ciphertext, ENCRYPTED, clen)){ cli_putstr_P(PSTR("\r\n>>FAIL (no content match)<<")); return; }else{ cli_putstr_P(PSTR("\r\n>>OK<<")); } } cli_putstr_P(PSTR("\r\ndecrypting: ...")); rc = rsa_decrypt_pkcs1v15(plaintext, &plen, ciphertext, clen, &priv_key, seed_out); if(rc){ cli_putstr_P(PSTR("\r\nERROR: rsa_decrypt_pkcs1v15 returned: ")); cli_hexdump_byte(rc); return; } cli_putstr_P(PSTR("\r\n\r\nplaintext:")); cli_hexdump_block(plaintext, plen, 4, 16); cli_putstr_P(PSTR("\r\n\r\nseed (out):")); cli_hexdump_block(seed_out, sizeof(SEED), 4, 16); free(ciphertext); free(plaintext); }
unsigned char SkipJack_test(void) { unsigned char ret=0; memcpy_P(SkipJack_Test_Key,SkipJack_Test1_Key,sizeof(SkipJack_Test1_Key)); memcpy_P(SkipJack_Test_Plain,SkipJack_Test1_Plain,sizeof(SkipJack_Test1_Plain)); SkipJack_Enc(SkipJack_Test_Plain, SkipJack_Test_Key); if(memcmp_P(SkipJack_Test_Plain,SkipJack_Test1_Cipher,sizeof(SkipJack_Test1_Cipher))) { ret|=1; } memcpy_P(SkipJack_Test_Key,SkipJack_Test1_Key,sizeof(SkipJack_Test1_Key)); memcpy_P(SkipJack_Test_Plain,SkipJack_Test1_Cipher,sizeof(SkipJack_Test1_Cipher)); SkipJack_Dec(SkipJack_Test_Plain, SkipJack_Test_Key); if(memcmp_P(SkipJack_Test_Plain,SkipJack_Test1_Plain,sizeof(SkipJack_Test1_Plain))) { ret|=2; } memcpy_P(SkipJack_Test_Key,SkipJack_Test2_Key,sizeof(SkipJack_Test2_Key)); memcpy_P(SkipJack_Test_Plain,SkipJack_Test2_Plain,sizeof(SkipJack_Test2_Plain)); SkipJack_Enc(SkipJack_Test_Plain, SkipJack_Test_Key); if(memcmp_P(SkipJack_Test_Plain,SkipJack_Test2_Cipher,sizeof(SkipJack_Test2_Cipher))) { ret|=4; } memcpy_P(SkipJack_Test_Key,SkipJack_Test2_Key,sizeof(SkipJack_Test2_Key)); memcpy_P(SkipJack_Test_Plain,SkipJack_Test2_Cipher,sizeof(SkipJack_Test2_Cipher)); SkipJack_Dec(SkipJack_Test_Plain, SkipJack_Test_Key); if(memcmp_P(SkipJack_Test_Plain,SkipJack_Test2_Plain,sizeof(SkipJack_Test2_Plain))) { ret|=8; } return ret; }
void test_vector(void *key, void *iv, const void *ref){ rabbit_ctx_t ctx; uint8_t fail=0; cli_putstr_P(PSTR("\r\n testing with\r\n key: ")); cli_hexdump(key, 16); cli_putstr_P(PSTR("\r\n iv: ")); if(iv){ cli_hexdump(iv, 8); }else{ cli_putstr_P(PSTR("[no iv]")); } rabbit_init(key, 128, iv, &ctx); rabbit_gen(&ctx); if(!ref || (memcmp_P(ctx.buffer, ref, 16))!=0){ fail = 1; cli_putstr_P(PSTR("\r\n S[0]: ")); cli_hexdump(ctx.buffer, 16); } ctx.buffer_idx=16; rabbit_gen(&ctx); if(!ref || (memcmp_P(ctx.buffer, ref, 16))!=0){ fail = 1; cli_putstr_P(PSTR("\r\n S[0]: ")); cli_hexdump(ctx.buffer, 16); } ctx.buffer_idx=16; rabbit_gen(&ctx); if(!ref || (memcmp_P(ctx.buffer, ref, 16))!=0){ fail = 1; cli_putstr_P(PSTR("\r\n S[0]: ")); cli_hexdump(ctx.buffer, 16); } if(ref){ cli_putstr_P(fail?PSTR("\r\n [fail]"):PSTR("\r\n [ok]")); } cli_putstr_P(PSTR("\r\n")); }
/** Recursively unwraps the given locally stored attribute (in PROGMEM space), searching for UUIDs to match against * the given UUID list. As matches are found, they are indicated in the UUIDMatch flag list. * * \param[in] UUIDList List of UUIDs which must be matched within the service attribute table * \param[in] TotalUUIDs Total number of UUIDs stored in the UUID list * \param[in, out] UUIDMatchFlags Array of flags indicating which UUIDs in the list have already been matched * \param[in] CurrAttribute Pointer to the current attribute to search through * * \return True if all the UUIDs given in the UUID list appear in the given attribute table, false otherwise */ static void SDP_CheckUUIDMatch(uint8_t UUIDList[][UUID_SIZE_BYTES], const uint8_t TotalUUIDs, uint16_t* const UUIDMatchFlags, const void* CurrAttribute) { uint8_t CurrAttributeType = (pgm_read_byte(CurrAttribute) & ~0x07); /* Check the data type of the current attribute value - if UUID, compare, if Sequence, unwrap and recurse */ if (CurrAttributeType == SDP_DATATYPE_UUID) { uint16_t CurrUUIDMatchMask = (1 << 0); /* Look for matches in the UUID list against the current attribute UUID value */ for (uint8_t i = 0; i < TotalUUIDs; i++) { /* Check if the current unmatched UUID is identical to the search UUID */ if (!(*UUIDMatchFlags & CurrUUIDMatchMask) && !(memcmp_P(UUIDList[i], (CurrAttribute + 1), UUID_SIZE_BYTES))) { /* Indicate match found for the current attribute UUID and early-abort */ *UUIDMatchFlags |= CurrUUIDMatchMask; break; } CurrUUIDMatchMask <<= 1; } } else if (CurrAttributeType == SDP_DATATYPE_Sequence) { uint8_t SequenceHeaderSize; uint16_t SequenceSize = SDP_GetLocalAttributeContainerSize(CurrAttribute, &SequenceHeaderSize); CurrAttribute += SequenceHeaderSize; /* Recursively unwrap the sequence container, and re-search its contents for UUIDs */ while (SequenceSize) { uint8_t InnerHeaderSize; uint16_t InnerSize = SDP_GetLocalAttributeContainerSize(CurrAttribute, &InnerHeaderSize); /* Recursively search of the next element in the sequence, trying to match UUIDs with the UUID list */ SDP_CheckUUIDMatch(UUIDList, TotalUUIDs, UUIDMatchFlags, CurrAttribute); /* Skip to the next element in the sequence */ SequenceSize -= InnerHeaderSize + InnerSize; CurrAttribute += InnerHeaderSize + InnerSize; } } }
void Check (int line, const char *s1, const char *s2, int clr, int pnt) { char t1[300]; char *sp; char *rp; if (strlen_P(s1) > sizeof(t1) - 1) exit (1); strcpy_P (t1, s1); sp = t1; rp = strsep_P (&sp, s2); if (rp != t1) { PRINTFLN (line, "false return value"); EXIT (5000 + line); } if (clr < 0) { if (strcmp_P (t1, s1)) { PRINTFLN (line, "string is changed"); EXIT (line); } } else { if (strlen (t1) != (size_t)clr) { PRINTFLN (line, "strlen: expect= %d result= %d", clr, strlen (t1)); EXIT (1000 + line); } if (memcmp_P (t1, s1, clr) || t1[clr] || strcmp_P (t1 + clr + 1, s1 + clr + 1)) { PRINTFLN (line, "string mismatch"); EXIT (2000 + line); } } if (pnt < 0) { if (sp) { PRINTFLN (line, "sp is not a NULL"); EXIT (3000 + line); } } else { if (sp != t1 + pnt) { PRINTFLN (line, "sp: expect= %d result= %d", pnt, sp - t1); EXIT (4000 + line); } } }
bool HMC5883L::begin() { // Read the device identity register uint8_t id[3]; twi.begin(this); twi.write((uint8_t) IDENTITY); twi.read(id, sizeof(id)); twi.end(); // Sanity check the identity static const uint8_t ID[3] __PROGMEM = { 'H', '4', '3' }; if (memcmp_P(id, ID, sizeof(ID))) return (false); // Write configuration return (write_config()); }
/* // - FontGet(char match, char *buf) // - Copies the character 'match' into // - the buffer. // - Returns - nothing */ void FontGet(char match, char *buf) { // copies the character "match" into the buffer uint8_t y; PGM_P p; for(y=0; y<FONT_SIZE; y++) { memcpy_P(&p, &font[y], sizeof(PGM_P)); if(memcmp_P(&match, p,1)==0) { memcpy_P(buf, p, 7); return; } } // NO MATCH? FontGet('?', buf); }
static int load_tbc (const prog_char *data, avr_tenc_element_t *element) { UWORD length; if (memcmp_P ("tenc", data, 4) != 0) { return -1; } length = avr_tenc_decode_int (data + 4); /* Skip over the first header. */ data += 6; if (avr_tenc_walk_to_element (data, &length, "tbcL", element) < 0) { return -1; } return 0; }
static void flash_page(uint32_t page, uint8_t *buf) { uint16_t i; uint8_t sreg; #ifdef TFTP_DEBUG_DO_NOT_FLASH return; #endif #if FLASHEND > UINT16_MAX if (memcmp_PF(buf, (uint_farptr_t)page, SPM_PAGESIZE) == 0) #else if (memcmp_P(buf, (PGM_VOID_P)page, SPM_PAGESIZE) == 0) #endif return; /* no changes */ /* Disable interrupts. */ sreg = SREG; cli(); eeprom_busy_wait(); boot_page_erase(page); boot_spm_busy_wait(); for(i = 0; i < SPM_PAGESIZE; i += 2) { /* Set up little-endian word. */ uint16_t w = *buf++; w += (*buf++) << 8; boot_page_fill (page + i, w); } boot_page_write (page); boot_spm_busy_wait(); /* Reenable RWW-section again. */ boot_rww_enable (); /* Re-enable interrupts (if they were ever enabled). */ SREG = sreg; }
int main () { /* Empty input. */ CHECK (-1, (*(char *)v.i == FILL), "", "%hhd", v.i); CHECK (-1, (*(char *)v.i == FILL), "", " %hhd", v.i); CHECK (-1, (*(char *)v.i == FILL), " ", " %hhd", v.i); CHECK (-1, (*(char *)v.i == FILL), " ", " %hhd", v.i); CHECK (-1, (*(char *)v.i == FILL), "\t\n\v\f\r", " %hhd", v.i); /* Normal conversion. */ CHECK (1, (v.i[0] == 0 && v.i[1] == FILL), "0", "%hhd", v.i); CHECK ( 6, !memcmp_P (v.i, PVEC (1, 127, -128, -2, -1, -1), 6), "1 127 128 255 32767 -2", "%hhd %hhd %hhd %hhd %hhd %hhd", v.i + 0, v.i + 1, v.i + 2, v.i + 5, v.i + 4, v.i + 3); /* All possible conversion types. */ CHECK ( 8, !memcmp_P (v.i, PVEC (1, 2, 3, 4, 5, 6, 7, 14, 8), 9), "1 2 3 4 5 6 7 8", "%hhd %hhu %hhi %hho %hhx %hhX %hhp %hhn %hhd", v.i + 0, v.i + 1, v.i + 2, v.i + 3, v.i + 4, v.i + 5, v.i + 6, v.i + 7, v.i + 8); /* Width field. */ CHECK (1, v.i[0] == 12 && v.i[1] == FILL, "123", "%2hhd", v.i); CHECK (1, v.i[0] == 98 && v.i[1] == FILL, "00000000009876", "%12hhd", v.i); /* A few conversions. */ CHECK (2, !memcmp_P (v.i, PVEC (1,2), 2) && (v.i[2] == FILL), "1 2", "%hhd%hhd", v.i, v.i + 1); CHECK (2, !memcmp_P (v.i, PVEC (1,3), 2) && (v.i[2] == FILL), "1+3", "%hhd%hhd", v.i, v.i + 1); CHECK (2, !memcmp_P (v.i, PVEC (1,-1), 2) && (v.i[2] == FILL), "1-1", "%hhd%hhd", v.i, v.i + 1); /* Suppress a writing. */ CHECK (0, (*(char *)v.i == FILL), "123", "%*hhd", v.i); CHECK (2, !memcmp_P (v.i, PVEC (1,3), 2) && (v.i[2] == FILL), "1 2 3", "%hhd%*hhd%hhd", v.i, v.i + 1); return 0; }
// "mycommand ... .... ..." // ^ ^ ^ // cmdname | | // cmdname+len | // line_end static BOOL handle_global_command(const uint8_t *cmdname, size_t len, const uint8_t *line_end) { const global_command_t *cmd_ptr = global_command_table; global_command_t cmd; memcpy_P(&cmd, cmd_ptr, sizeof(global_command_t)); while(NULL != cmd.name) { if (memcmp_P(cmdname, cmd.name, len)==0 && strlen_P(cmd.name) <= len) { if (!(*cmd.handler)(cmdname+len, line_end)) { console_puts_P(PSTR("Error")); console_newline(); } return TRUE; } memcpy_P(&cmd, ++cmd_ptr, sizeof(global_command_t)); } return FALSE; }
void webif_data(uint8_t id, eth_frame_t *frame, uint16_t len) { ip_packet_t *ip = (void*)(frame->data); tcp_packet_t *tcp = (void*)(ip->data); char *req = (void*)tcp_get_data(tcp); char *buf = (void*)(tcp->data), *buf_ptr = buf; char *url, *p, *params, *name, *value; if(!len) return; if( (memcmp_P(req, PSTR("GET "), 4) == 0) && ((p = strchr(req + 4, ' ')) != 0) ) { url = req + 4; *p = 0; if((params = strchr(url, '?'))) *(params++) = 0; if(strcmp_P(url, PSTR("/")) == 0) { if(params==NULL) { send_Uart_str(" No params!"); send_Uart(13); }else { send_Uart_str(" With params!"); send_Uart(13); } while(params) { if((p = strchr(params, '&'))) *(p++) = 0; name = params; if((value = strchr(name, '='))) *(value++) = 0; if( (strcmp_P(name, PSTR("led")) == 0 ) && value ) { if(strcmp_P(value, PSTR("on")) == 0) led_on() else if(strcmp_P(value, PSTR("off")) == 0) led_off() } else if( (strcmp_P(name, PSTR("lang")) == 0) && value ) { if(strcmp_P(value, PSTR("en")) == 0) lang_ru = 0; else if(strcmp_P(value, PSTR("ru")) == 0) lang_ru = 1; } params = p; } fill_buf_p(&buf_ptr, webif_200_header); fill_buf_p(&buf_ptr, PSTR("<pre>")); if(!lang_ru) { fill_buf_p(&buf_ptr, PSTR("<p align='right'>[<b>EN</b> | " "<a href='/?lang=ru'>RU</a>]</p>")); } else { fill_buf_p(&buf_ptr, PSTR("<p align='right'>[<a href='/?lang=en'>EN</a> | " "<b>RU</b>]</p>")); } if((!led_state)&&(!lang_ru)) fill_buf_p(&buf_ptr, PSTR("Led is OFF. Turn <a href='/?led=on'>on</a>.")); else if(led_state &&(!lang_ru)) fill_buf_p(&buf_ptr, PSTR("Led is ON. Turn <a href='/?led=off'>off</a>.")); else if((!led_state)&&(lang_ru)) fill_buf_p(&buf_ptr, PSTR("Светодиод выключен. <a href='/?led=on'>Включить</a>.")); else if(led_state &&(lang_ru)) fill_buf_p(&buf_ptr, PSTR("Светодиод включен. <a href='/?led=off'>Выключить</a>.")); fill_buf_p(&buf_ptr, PSTR("</pre>")); }
int HTTP::Client::get(const char* url, uint32_t ms) { if (m_sock == NULL) return (-1); const uint8_t PREFIX_MAX = 7; uint16_t port = 80; char hostname[HOSTNAME_MAX]; uint32_t start; uint8_t i; int res; char c; // Parse given url for hostname if (memcmp_P(url, PSTR("http://"), PREFIX_MAX) == 0) url += PREFIX_MAX; i = 0; while (1) { c = *url; hostname[i] = c; if (c == 0) break; url += 1; if ((c == '/') || (c == ':')) break; i += 1; if (i == sizeof(hostname)) return (-2); } if (c != 0) hostname[i] = 0; // Parse url for port number if (c == ':') { char num[16]; i = 0; while (isdigit(c = *url)) { url += 1; num[i++] = c; if (i == sizeof(num)) return (-2); } if (i == 0) return (-2); num[i] = 0; port = atoi(num); if (c == '/') url += 1; } // Connect to the server res = m_sock->connect((const char*) hostname, port); if (res != 0) goto error; while ((res = m_sock->isconnected()) == 0) Watchdog::delay(16); if (res == 0) res = -3; if (res < 0) goto error; // Send a HTTP request m_sock->puts_P(PSTR("GET /")); m_sock->puts(url); m_sock->puts_P(PSTR(" HTTP/1.1" CRLF "Host: ")); m_sock->puts(hostname); m_sock->puts_P(PSTR(CRLF "Connection: close" CRLF CRLF)); m_sock->flush(); // Wait for the response start = Watchdog::millis(); while (((res = m_sock->available()) == 0) && ((ms == 0L) || (Watchdog::millis() - start < ms))) Watchdog::delay(16); if (res == 0) res = -4; if (res < 0) goto error; on_response(hostname, url); res = 0; // Close the connect and reopen for additional get error: m_sock->disconnect(); m_sock->close(); m_sock->open(Socket::TCP, 0, 0); return (res); }
void testrun_aes128_eax(void){ uint8_t key[16]; uint8_t nonce[16]; uint8_t header[8]; uint8_t tag[16]; uint8_t msg[21]; uint8_t msg_len; PGM_VOID_P msg_p; PGM_VOID_P cipher_p; uint8_t i, r; bcal_eax_ctx_t ctx; msg_p = eax_msg; cipher_p = eax_cipher; for(i=0; i<10; ++i){ cli_putstr_P(PSTR("\r\n\r\n** AES128-EAX-TEST #")); cli_putc('0'+i); cli_putstr_P(PSTR(" **")); msg_len = pgm_read_byte(eax_msg_len+i); memcpy_P(key, eax_key+16*i, 16); memcpy_P(nonce, eax_nonce+16*i, 16); memcpy_P(header, eax_header+8*i, 8); memcpy_P(msg, msg_p, msg_len); msg_p = (uint8_t*)msg_p+msg_len; cli_putstr_P(PSTR("\r\n key: ")); cli_hexdump(key, 16); cli_putstr_P(PSTR("\r\n msg: ")); if(msg_len){ cli_hexdump(msg, msg_len); } cli_putstr_P(PSTR("\r\n nonce: ")); cli_hexdump(nonce, 16); cli_putstr_P(PSTR("\r\n header: ")); cli_hexdump(header, 8); r = bcal_eax_init(&aes128_desc, key, 128, &ctx); cli_putstr_P(PSTR("\r\n init = 0x")); cli_hexdump(&r, 1); if(r) return; bcal_eax_loadNonce(nonce, 16*8, &ctx); bcal_eax_addLastHeader(header, 8*8, &ctx); bcal_eax_encLastBlock(msg, msg_len*8, &ctx); bcal_eax_ctx2tag(tag, 128, &ctx); cli_putstr_P(PSTR("\r\n cipher: ")); cli_hexdump_block(msg, msg_len, 4, 16); cli_putstr_P(PSTR("\r\n tag: ")); cli_hexdump_block(tag, 16, 4, 16); if(memcmp_P(msg, cipher_p, msg_len)){ cli_putstr_P(PSTR("\r\n cipher: [fail]\r\n should: ")); memcpy_P(msg, cipher_p, msg_len); cli_hexdump_block(msg, msg_len, 4, 16); }else{ cli_putstr_P(PSTR("\r\n cipher: [pass]")); } cipher_p = ((uint8_t*)cipher_p)+msg_len; // * if(memcmp_P(tag, cipher_p, 16)){ cli_putstr_P(PSTR("\r\n tag: [fail]")); }else{ cli_putstr_P(PSTR("\r\n tag: [pass]")); } cipher_p = ((uint8_t*)cipher_p)+16; bcal_eax_free(&ctx); } }
int16_t ecmd_parse_command(char *cmd, char *output, uint16_t len) { #ifdef DEBUG_ECMD debug_printf("called ecmd_parse_command %s\n", cmd); #endif #ifdef ECMD_LOG_VIA_SYSLOG if (0 == strchr(cmd, ECMD_STATE_MAGIC)) syslog_sendf_P(PSTR("ecmd: %s"), cmd); #endif #ifdef ECMD_REMOVE_BACKSPACE_SUPPORT uint8_t i = 0; while (cmd[i] != '\0' && cmd[i] != ECMD_STATE_MAGIC && i < ECMD_OUTPUTBUF_LENGTH) { // search until end of string if (cmd[i] == '\b') { // check cmd for backspaces uint16_t cmdlen = strlen(cmd + i); memmove(cmd + i - 1, cmd + i + 1, cmdlen); // we found a backspace, so we move all chars backwards i--; // and decrement char counter } else { i++; // goto char } } #endif /* ECMD_REMOVE_BACKSPACE_SUPPORT */ #ifdef ALIASCMD_SUPPORT if (cmd[0] == '$') { // alias command names start with $ #ifdef DEBUG_ECMD debug_printf("try alias\n"); #endif if (aliascmd_decode(cmd) == NULL) { // command not found in alias list #ifdef DEBUG_ECMD debug_printf("Alias failed\n"); #endif } else { #ifdef DEBUG_ECMD debug_printf("new command: %s\n", cmd); #endif } } #endif /* ALIASCMD_SUPPORT */ if (strlen(cmd) < 2) { #ifdef DEBUG_ECMD debug_printf("cmd is too short\n"); #endif return 0; } int ret = -1; char *text = NULL; int16_t(*func) (char *, char *, uint16_t) = NULL; uint8_t pos = 0; while (1) { /* load pointer to text */ text = (char *) pgm_read_word(&ecmd_cmds[pos].name); #ifdef DEBUG_ECMD debug_printf("loaded text addres %p: \n", text); #endif /* return if we reached the end of the array */ if (text == NULL) break; #ifdef DEBUG_ECMD debug_printf("text is: \"%S\"\n", text); #endif /* else compare texts */ if (memcmp_P(cmd, text, strlen_P(text)) == 0) { #ifdef DEBUG_ECMD debug_printf("found match\n"); #endif cmd += strlen_P(text); func = (void *) pgm_read_word(&ecmd_cmds[pos].func); break; } pos++; } #ifdef DEBUG_ECMD debug_printf("rest cmd: \"%s\"\n", cmd); #endif ACTIVITY_LED_ECMD; if (func != NULL) ret = func(cmd, output, len); if (output != NULL) { if (ret == -1) { memcpy_P(output, PSTR("parse error"), 11); ret = 11; } else if (ret == 0) { output[0] = 'O'; output[1] = 'K'; ret = 2; } } return ret; }
boolean HTTPServer::checkRequest(const char* method, const __FlashStringHelper* path) { char* payload = (char*)this->payload(); uint16_t length = payloadLength(); uint16_t endOfMethod; uint16_t pos; // Is there a TCP request ready for us? if (!havePacket()) return false; // Does the method match? endOfMethod = strlen_P(method); if (memcmp_P(payload, method, endOfMethod) != 0) { // Wrong method return false; } // Check there is a space after the method if (payload[endOfMethod] != ' ') { // No space after method return false; } // Do the paths match? const char *matchpath = reinterpret_cast<const char *>(path); uint8_t maxlen = length - endOfMethod - 1; bool allowAny = false; _pathPtr = &payload[endOfMethod + 1]; for(uint8_t i=0; i < maxlen; i++) { char match = pgm_read_byte(matchpath + i); // Have we got the end of the path section in the HTTP request? if (isWhitespace(_pathPtr[i]) || _pathPtr[i] == '?') { if (match == '\0') { // Both ended at the same time _pathPtr[i] = '\0'; break; } else { // Path ended before the string we are trying to match against return false; } } // Allow anything after a '#' character if (match == '#') allowAny = true; // Allow any character to match a '?' if (match == '?' || allowAny) continue; // Do they match up? if (_pathPtr[i] != match) return false; } // Find the start of the body section _bodyPtr = NULL; for(pos = endOfMethod+1; pos < length-1; pos++) { if (payload[pos] == '\n' && (payload[pos-2] == '\n' || payload[pos-1] == '\n')) { // Store the location of the start of the body _bodyPtr = &payload[pos+1]; // For convenience NULL-terminate the body payload[length] = '\0'; break; } } return true; }
/** * \brief Parse the header part of the xPL message line by line * \param _xPLMessage the result xPL message * \param _buffer the line to parse * \param _line the line number */ byte xPL::AnalyseHeaderLine(xPL_Message* _xPLMessage, char* _buffer, byte _line) { switch (_line) { case XPL_MESSAGE_TYPE_IDENTIFIER: //message type identifier if (memcmp_P(_buffer,PSTR("xpl-"),4)==0) //xpl { if (memcmp_P(_buffer+4,PSTR("cmnd"),4)==0) //command type { _xPLMessage->type=XPL_CMND; //xpl-cmnd } else if (memcmp_P(_buffer+4,PSTR("stat"),4)==0) //statut type { _xPLMessage->type=XPL_STAT; //xpl-stat } else if (memcmp_P(_buffer+4,PSTR("trig"),4)==0) // trigger type { _xPLMessage->type=XPL_TRIG; //xpl-trig } } else { return 0; //unknown message } return 1; break; case XPL_OPEN_HEADER: //header begin if (memcmp(_buffer,"{",1)==0) { return 2; } else { return -2; } break; case XPL_HOP_COUNT: //hop if (sscanf_P(_buffer, XPL_HOP_COUNT_PARSER, &_xPLMessage->hop)) { return 3; } else { return -3; } break; case XPL_SOURCE: //source if (sscanf_P(_buffer, XPL_SOURCE_PARSER, &_xPLMessage->source.vendor_id, &_xPLMessage->source.device_id, &_xPLMessage->source.instance_id) == 3) { return 4; } else { return -4; } break; case XPL_TARGET: //target if (sscanf_P(_buffer, XPL_TARGET_PARSER, &_xPLMessage->target.vendor_id, &_xPLMessage->target.device_id, &_xPLMessage->target.instance_id) == 3) { return 5; } else { if(memcmp(_xPLMessage->target.vendor_id,"*", 1) == 0) // check if broadcast message { return 5; } else { return -5; } } break; case XPL_CLOSE_HEADER: //header end if (memcmp(_buffer,"}",1)==0) { return 6; } else { return -6; } break; case XPL_SCHEMA_IDENTIFIER: //schema sscanf_P(_buffer, XPL_SCHEMA_PARSER, &_xPLMessage->schema.class_id, &_xPLMessage->schema.type_id); return 7; break; case XPL_OPEN_SCHEMA: //header begin if (memcmp(_buffer,"{",1)==0) { return 8; } else { return -8; } break; } return -100; }
int16_t ecmd_parse_command(char *cmd, char *output, uint16_t len) { #ifdef DEBUG_ECMD debug_printf("called ecmd_parse_command %s\n", cmd); #endif #ifdef ALIASCMD_SUPPORT if (cmd[0] == '$') { // alias command names start with $ #ifdef DEBUG_ECMD debug_printf("try alias\n"); #endif if (aliascmd_decode(cmd) == NULL) { // command not found in alias list #ifdef DEBUG_ECMD debug_printf("Alias failed\n"); #endif }else{ #ifdef DEBUG_ECMD debug_printf("new command: %s\n", cmd); #endif } } #endif if (strlen(cmd) < 2) { #ifdef DEBUG_ECMD debug_printf("cmd is too short\n"); #endif return 0; } int ret = -1; char *text = NULL; int16_t (*func)(char*, char*, uint16_t) = NULL; uint8_t pos = 0; while (1) { /* load pointer to text */ text = (char *)pgm_read_word(&ecmd_cmds[pos].name); #ifdef DEBUG_ECMD debug_printf("loaded text addres %p: \n", text); #endif /* return if we reached the end of the array */ if (text == NULL) break; #ifdef DEBUG_ECMD debug_printf("text is: \"%S\"\n", text); #endif /* else compare texts */ if (memcmp_P(cmd, text, strlen_P(text)) == 0) { #ifdef DEBUG_ECMD debug_printf("found match\n"); #endif cmd += strlen_P(text); func = (void *)pgm_read_word(&ecmd_cmds[pos].func); break; } pos++; } #ifdef DEBUG_ECMD debug_printf("rest cmd: \"%s\"\n", cmd); #endif if (func != NULL) ret = func(cmd, output, len); if (output != NULL) { if (ret == -1) { memcpy_P(output, PSTR("parse error"), 11); ret = 11; } else if (ret == 0) { output[0] = 'O'; output[1] = 'K'; ret = 2; } } return ret; }
enum ws_frame_type ws_parse_handshake(const uint8_t *input_frame, size_t input_len, struct handshake *hs) { const char *input_ptr = (const char *)input_frame; const char *end_ptr = (const char *)input_frame + input_len; // measure resource size char *first = strchr((const char *)input_frame, ' '); if (!first) return WS_ERROR_FRAME; first++; char *second = strchr(first, ' '); if (!second) return WS_ERROR_FRAME; if (hs->resource) { free(hs->resource); hs->resource = NULL; } hs->resource = (char *)malloc(second - first + 1); // +1 is for \x00 symbol assert(hs->resource); if (sscanf_P(input_ptr, PSTR("GET %s HTTP/1.1\r\n"), hs->resource) != 1) return WS_ERROR_FRAME; input_ptr = strstr_P(input_ptr, rn) + 2; /* parse next lines */ #define input_ptr_len (input_len - (input_ptr - input_frame)) #define prepare(x) do { if (x) { free(x); x = NULL; } } while (0) uint8_t connection_flag = FALSE; uint8_t upgrade_flag = FALSE; while (input_ptr < end_ptr && input_ptr[0] != '\r' && input_ptr[1] != '\n') { if (memcmp_P(input_ptr, host, strlen_P(host)) == 0) { input_ptr += strlen_P(host); prepare(hs->host); hs->host = get_upto_linefeed(input_ptr); } else if (memcmp_P(input_ptr, origin, strlen_P(origin)) == 0) { input_ptr += strlen_P(origin); prepare(hs->origin); hs->origin = get_upto_linefeed(input_ptr); } else if (memcmp_P(input_ptr, protocol, strlen_P(protocol)) == 0) { input_ptr += strlen_P(protocol); prepare(hs->protocol); hs->protocol = get_upto_linefeed(input_ptr); } else if (memcmp_P(input_ptr, key1, strlen_P(key1)) == 0) { input_ptr += strlen_P(key1); prepare(hs->key1); hs->key1 = get_upto_linefeed(input_ptr); } else if (memcmp_P(input_ptr, key2, strlen_P(key2)) == 0) { input_ptr += strlen_P(key2); prepare(hs->key2); hs->key2 = get_upto_linefeed(input_ptr); } else if (memcmp_P(input_ptr, key, strlen_P(key)) == 0) { input_ptr += strlen_P(key); prepare(hs->key); hs->key = get_upto_linefeed(input_ptr); } else if (memcmp_P(input_ptr, version, strlen_P(version)) == 0) { input_ptr += strlen_P(version); hs->version = atoi(get_upto_linefeed(input_ptr)); } else if (memcmp_P(input_ptr, connection, strlen_P(connection)) == 0) { connection_flag = TRUE; } else if (memcmp_P(input_ptr, upgrade2, strlen_P(upgrade2)) == 0) { upgrade_flag = TRUE; } else if (memcmp_P(input_ptr, upgrade, strlen_P(upgrade)) == 0) { upgrade_flag = TRUE; } input_ptr = strstr_P(input_ptr, rn) + 2; } // we have read all data, so check them if (!hs->host || !hs->origin || ((!hs->key1 || !hs->key2) && (!hs->key)) || !connection_flag || !upgrade_flag) return WS_ERROR_FRAME; input_ptr += 2; // skip empty line if (hs->version == 8) { if (end_ptr - input_ptr < 8) return WS_INCOMPLETE_FRAME; memcpy(hs->key3, input_ptr, 8); } return WS_OPENING_FRAME; }
int main () { void *p; /* Fill all EEPROM. */ for (p = 0; p <= (void *)E2END; p++) eeprom_write_byte (p, (int)(p + 1)); /* Update a byte. */ { unsigned char *p = (unsigned char *)1; eeprom_update_byte (p, 2); /* the same value */ if (!eeprom_is_ready ()) exit (__LINE__); if (eeprom_read_byte (p) != 2) exit (__LINE__); eeprom_update_byte (p, 0x12); /* different value */ if (eeprom_is_ready ()) exit (__LINE__); if (eeprom_read_byte (p) != 0x12) exit (__LINE__); } /* Update a word. */ { unsigned int *p = (unsigned int *)2; eeprom_update_word (p, 0x0403); /* the same value */ if (!eeprom_is_ready ()) exit (__LINE__); if (eeprom_read_word (p) != 0x0403) exit (__LINE__); eeprom_update_word (p, 0x0413); if (eeprom_is_ready ()) exit (__LINE__); if (eeprom_read_word (p) != 0x0413) exit (__LINE__); eeprom_update_word (p, 0x1413); if (!eeprom_is_ready ()) exit (__LINE__); if (eeprom_read_word (p) != 0x1413) exit (__LINE__); } /* Update a double word. */ { unsigned long *p = (unsigned long *)4; eeprom_update_dword (p, 0x08070605); /* the same value */ if (!eeprom_is_ready ()) exit (__LINE__); if (eeprom_read_dword (p) != 0x08070605) exit (__LINE__); eeprom_update_dword (p, 0x08070615); if (eeprom_is_ready ()) exit (__LINE__); if (eeprom_read_dword (p) != 0x08070615) exit (__LINE__); eeprom_update_dword (p, 0x08071615); if (!eeprom_is_ready ()) exit (__LINE__); if (eeprom_read_dword (p) != 0x08071615) exit (__LINE__); eeprom_update_dword (p, 0x08171615); if (!eeprom_is_ready ()) exit (__LINE__); if (eeprom_read_dword (p) != 0x08171615) exit (__LINE__); eeprom_update_dword (p, 0x18171615); if (!eeprom_is_ready ()) exit (__LINE__); if (eeprom_read_dword (p) != 0x18171615) exit (__LINE__); } /* Update a block. */ { unsigned char *p = (unsigned char *)8; unsigned char s[5]; memcpy_P (s, PSTR ("\x09\x0A\x0B\x0C\x0D"), 5); eeprom_update_block (s, p, 5); if (!eeprom_is_ready ()) exit (__LINE__); memset (s, 0, sizeof (s)); eeprom_read_block (s, p, 5); if (memcmp_P (s, PSTR ("\x09\x0A\x0B\x0C\x0D"), 5)) exit (__LINE__); memcpy_P (s, PSTR ("\x19\x0A\x0B\x0C\x0D"), 5); eeprom_update_block (s, p, 5); if (eeprom_is_ready ()) exit (__LINE__); memset (s, 0, sizeof (s)); eeprom_read_block (s, p, 5); if (memcmp_P (s, PSTR ("\x19\x0A\x0B\x0C\x0D"), 5)) exit (__LINE__); memcpy_P (s, PSTR ("\x19\x0A\x0B\x0C\x1D"), 5); eeprom_update_block (s, p, 5); if (!eeprom_is_ready ()) exit (__LINE__); memset (s, 0, sizeof (s)); eeprom_read_block (s, p, 5); if (memcmp_P (s, PSTR ("\x19\x0A\x0B\x0C\x1D"), 5)) exit (__LINE__); memcpy_P (s, PSTR ("\x1A\x1B\x1C"), 3); eeprom_update_block (s, p + 1, 1); eeprom_update_block (s + 1, p + 2, 2); } /* Check all EEPROM. */ for (p = 0; p <= (void *)E2END; p++) { unsigned char c; c = (int)p + ((p && (p < (void *)13)) ? 0x11 : 1); if (eeprom_read_byte (p) != c) exit (__LINE__); } return 0; }