crypto_error_t crypto_mac(bytestring_t *dst, const bytestring_t *ctx, const bytestring_t *src) { unsigned u,v; unsigned char tmp[8]; unsigned char clr[8]; unsigned char alg; crypto_error_t retval; bytestring_t *padded_src; DES_key_schedule key_schedule; DES_key_schedule key_schedule2; bytestring_get_element(&alg,ctx,0); if (alg==CRYPTO_ALG_ISO9797_M3) { padded_src = bytestring_new(8); retval = crypto_pad(padded_src,ctx,src); if (retval!=CRYPTO_OK) { bytestring_free(padded_src); return retval; } memset(tmp,0,8); memcpy(&key_schedule,ctx->data+KS_HEADER_SIZE,DES_KS_SIZE); memcpy(&key_schedule2,ctx->data+KS_HEADER_SIZE+DES_KS_SIZE,DES_KS_SIZE); for (u=0; u<bytestring_get_size(padded_src)/8; u++) { for (v=0; v<8; v++) clr[v]=padded_src->data[u*8+v]^tmp[v]; DES_ecb_encrypt((const_DES_cblock *)clr, (DES_cblock *)tmp, &key_schedule, DES_ENCRYPT); } memcpy(clr,tmp,8); DES_ecb_encrypt((const_DES_cblock *)clr, (DES_cblock *)tmp, &key_schedule2, DES_DECRYPT); memcpy(clr,tmp,8); DES_ecb_encrypt((const_DES_cblock *)clr, (DES_cblock *)tmp, &key_schedule, DES_ENCRYPT); bytestring_assign_data(dst,8,tmp); bytestring_free(padded_src); } else return CRYPTO_ERROR_UNKNOWN_ALGORITHM; return CRYPTO_OK; }
static gboolean internal_load_image(CustomCellRendererFlexi *cr, const char *src, const char *mime_type) { GdkPixbufLoader *loader; bytestring_t *bs = bytestring_new_from_string(src); GError *err = NULL; if (bs==NULL) { internal_render_error(cr,"No image data."); return FALSE; } if (bs->width!=8) { internal_render_error(cr,"Image data must be octets."); bytestring_free(bs); return FALSE; } loader = gdk_pixbuf_loader_new_with_mime_type(mime_type,&err); if (!loader) goto internal_load_image_fail; if (gdk_pixbuf_loader_write(loader,bs->data,bs->len,&err)==FALSE) goto internal_load_image_fail; err=NULL; if (gdk_pixbuf_loader_close(loader,&err)==FALSE) goto internal_load_image_fail; cr->rendered_type = RENDER_PIXBUF; cr->rendered_value = (GdkPixbuf*) gdk_pixbuf_loader_get_pixbuf(loader); g_object_ref(cr->rendered_value); g_object_unref(loader); bytestring_free(bs); return TRUE; internal_load_image_fail: if (err!=NULL) { internal_render_error(cr,err->message); g_error_free(err); } if (bs) bytestring_free(bs); return FALSE; }
void headerbundle_free(headerbundle *hb) { // Free header contents for (int i = 0; i < hb->count; i++) { bytestring_free(hb->headers[i].key); bytestring_free(hb->headers[i].val); } // Free array of header structs xfree(hb->headers); // Free root struct xfree(hb); }
void queue_free(queue *q) { bytestring_free(q->name); storage_free(q->storage); xfree(q); }
void cardreader_free(cardreader_t *reader) { reader->finalize(reader); bytestring_free(reader->atr); cardreplay_free(reader->cardlog); free(reader->name); free(reader); }
// Parses a frame's command. Returns true iff progress was made. bool frameparser_parse_command(frameparser *fp, buffer *b) { log_printf(LOG_LEVEL_DEBUG, "frameparser_parse_command\n"); // Valid input in this state is a string followed by CR/LF or LF, which matches a known frame command // Try to find LF line terminator int lfpos = buffer_find_byte(b, '\x0A'); if (lfpos < 0) // No LF yet? { if (buffer_get_length(b) > LIMIT_FRAME_CMD_LINE_LEN) frameparser_set_error(fp, "Line length limit exceeded waiting for command"); return false; // No progress } else if (lfpos == 0) abort(); // Should never happen in this state // Figure out number of bytes in command string int len = lfpos; if (buffer_get_byte(b, len - 1) == '\x0D') len--; // Extract the command into a new bytestring bytestring *bs = bytestring_new(len); buffer_append_bytestring(b, bs, 0, len); bytestring_dump(bs); // Consume the current line buffer_consume(b, lfpos + 1); // Find the command code for this command frame_command cmd = frame_command_code(bytestring_get_bytes(bs), bytestring_get_length(bs)); // Clean up the bytestring bytestring_free(bs); // Make sure command is valid if (cmd == CMD_NONE) { frameparser_set_error(fp, "Unknown command"); return false; } // Set up a new frame structure to hold parsed data if (!fp->cur_frame) fp->cur_frame = frame_new(); // Store parsed data frame_set_command(fp->cur_frame, cmd); // Got a valid command, so headers should be next fp->state = FP_STATE_HEADER; return true; }
void frameparser_free(frameparser *fp) { if (fp->cur_frame) xfree(fp->cur_frame); if (fp->fin_frame) xfree(fp->fin_frame); if (fp->error) bytestring_free(fp->error); xfree(fp); }
crypto_error_t crypto_encrypt(bytestring_t *dst, const bytestring_t *ctx, const bytestring_t *src, const bytestring_t *iv) { unsigned pad_type; bytestring_t *padded_src; crypto_error_t retval; bytestring_get_element((unsigned char *)&pad_type,ctx,1); if (pad_type==0 && (bytestring_get_size(src)&0x7)==0) return crypto_cipher(dst,ctx,src,iv,DES_ENCRYPT); padded_src=bytestring_new(8); retval = crypto_pad(padded_src,ctx,src); if (retval==CRYPTO_OK) { retval = crypto_cipher(dst,ctx,padded_src,iv,DES_ENCRYPT); } bytestring_free(padded_src); return retval; }
/* static void update_dump(update_t *update, FILE* out) { update_item_t *item = update->items; fprintf(out,"Update version %s\n",update->update_version); while (item) { update_item_dump(item,out); item = item->next; } } */ static int update_load(update_t *update, const char *data, unsigned data_len) { char *ptr = (char *)data; unsigned ptr_len = data_len; char *data_end; char *value; update_item_t *item = NULL; bytestring_t *signature; bytestring_t *source; int signature_verified; #define fail_update(m) { log_printf(LOG_ERROR,"Failed to parse update information: %s",m); \ goto update_new_fail; } if ((value = tokenizer_get_record(&ptr,&ptr_len))==NULL) fail_update("Missing header"); if (strcmp(value,"header")!=0) fail_update("Incorrect header"); g_free(value); if ((value = tokenizer_get_field("version",&ptr,&ptr_len))==NULL) fail_update("missing version"); update->update_version = value; /* don't free value */ data_end = ptr; while ((value = tokenizer_get_record(&ptr,&ptr_len))!=NULL) { if (strcmp(value,"update")!=0) break; g_free(value); item = update_item_new(); if ((value = tokenizer_get_field("file",&ptr,&ptr_len))==NULL) fail_update("missing file name"); item->file = value; if ((value = tokenizer_get_field("url",&ptr,&ptr_len))==NULL) fail_update("missing url"); item->url = value; if ((value = tokenizer_get_field("required_version",&ptr,&ptr_len))==NULL) fail_update("missing required version"); item->required_version = value; if ((value = tokenizer_get_field("digest",&ptr,&ptr_len))==NULL) fail_update("missing digest"); bytestring_assign_digit_string(&item->digest,value); g_free(value); if (bytestring_get_size(&item->digest)!=SHA256_DIGEST_LENGTH) fail_update("incorrect digest length"); if ((value = tokenizer_get_field("message",&ptr,&ptr_len))==NULL) fail_update("missing message"); item->message = value; update->item_count++; item->next = update->items; update->items = item; item = NULL; data_end = ptr; } if (value==NULL) fail_update("missing section"); if (strcmp(value,"authentication")!=0) fail_update("missing authentication"); g_free(value); if ((value = tokenizer_get_field("signature",&ptr,&ptr_len))==NULL) fail_update("missing signature"); signature = bytestring_new(8); bytestring_assign_digit_string(signature,value); g_free(value); log_printf(LOG_DEBUG,"Verifying %d bit signature on update information (%d bytes), representing %d files.", bytestring_get_size(signature)*8,data_end-data,update->item_count); source = bytestring_new(8); bytestring_assign_data(source,data_end-data,(const unsigned char *)data); if (verify_signature(source,signature)==0) { log_printf(LOG_ERROR,"Signature verification failed on update information."); signature_verified = 0; update_clear(update); } else { log_printf(LOG_INFO,"Signature verification succeeded on update information."); signature_verified = 1; } bytestring_free(signature); bytestring_free(source); return signature_verified; update_new_fail: if (value) g_free(value); if (update) update_clear(update); if (item) update_item_free(item); return 0; }
// Unescapes a bytestring according to the rules used for headers: // "\r" => CR, "\n" => LF, "\c" => ":", "\\" => "\" // If the input bytestring is well-formed, it is consumed and a new bytestring // is returned. If the input bytestring is malformed, it is not consumed and // NULL is returned. static bytestring *unescape_header_bytestring(bytestring *in) { bytestring *out = NULL; bool success = true; size_t inlen = bytestring_get_length(in); int pos = 0; // Handle trivial case of zero-length input if (inlen == 0) return in; while (pos < inlen) { // Find next backslash int bspos = bytestring_find_byte(in, '\\', pos); if (bspos == -1) { // No backslash, can take the rest of the input verbatim if (!out) return in; // No transforms needed, so just return the input string // Create output string, if needed if (!out) out = bytestring_new(bytestring_get_length(in)); // Grab rest of input string size_t count = inlen - pos; bytestring_append_bytestring(out, in, pos, count); pos += count; } else { // There was a backslash, so we'll need to do some transforming // Create output string, if needed if (!out) out = bytestring_new(bytestring_get_length(in)); // Grab all characters before the backslash, if any if (bspos > 0) { // Copy everything before the backslash size_t count = bspos - pos; bytestring_append_bytestring(out, in, pos, count); pos += count; } // Process the character following the backslash if (bytestring_get_length(in) == (bspos + 1)) { success = false; // There is no following character break; } else { uint8_t c = bytestring_get_bytes(in)[bspos + 1]; if (c == '\\') bytestring_append_byte(out, '\\'); else if (c == 'r') bytestring_append_byte(out, '\x0D'); // CR else if (c == 'n') bytestring_append_byte(out, '\x0A'); // LF else if (c == 'c') bytestring_append_byte(out, ':'); else { success = false; // Invalid escape sequence break; } pos += 2; } } } // Handle errors if (!success) { if (out) bytestring_free(out); return NULL; } // All done bytestring_free(in); return out; }