int pe_populatecert(Pe *pe, void *cert, size_t size) { int rc; data_directory *dd = NULL; rc = pe_getdatadir(pe, &dd); if (rc < 0) return rc; if (size != dd->certs.size) return -1; void *mem = compute_mem_addr(pe, dd->certs.virtual_address); if (!mem) return -1; memcpy(mem, cert, size); uint64_t max_size = pe->maximum_size; uint32_t new_space; uint32_t page_size = sysconf(_SC_PAGESIZE); pe_extend_file(pe, 0, &new_space, page_size); uint64_t new_max_size = pe->maximum_size; mem = compute_mem_addr(pe, 0); msync(mem, new_max_size, MS_SYNC); new_max_size -= max_size; pe_shorten_file(pe, new_max_size); return 0; }
int pe_alloccert(Pe *pe, size_t size) { int rc; data_directory *dd = NULL; pe_clearcert(pe); uint32_t new_space = 0; rc = pe_extend_file(pe, size, &new_space, 8); if (rc < 0) return rc; rc = pe_getdatadir(pe, &dd); if (rc < 0) return rc; void *addr = compute_mem_addr(pe, new_space); /* We leave the whole list empty until finalize...*/ memset(addr, '\0', size); dd->certs.virtual_address = compute_file_addr(pe, addr); dd->certs.size += size; return 0; }
off_t __pe_updatemmap(Pe *pe, size_t shnum __attribute__((__unused__))) { /* This needs to write back the whole file: * 1) mz/pe/pe-o headers * 2) section headers and sections * 3) data directory table and data directories * * We also need to check if the signature is valid and if not, * make sure it's not in the data directory. */ struct mz_hdr *mzhdr = pe->state.pe.mzhdr; struct pe_hdr *pehdr = pe->state.pe.pehdr; if (pe->flags & PE_F_DIRTY) { off_t offset = 0; memcpy(pe->map_address + offset, mzhdr, sizeof(*mzhdr)); offset += le32_to_cpu(mzhdr->peaddr); memcpy(pe->map_address + offset, pehdr, sizeof(*pehdr)); } /* it's not dirty any more, so clear the flag. */ pe->flags &= ~PE_F_DIRTY; /* flush back to disk */ char *msync_start = ((char *) pe->map_address + (~(sysconf(_SC_PAGESIZE) -1 ))); data_directory *dd = NULL; int rc = pe_getdatadir(pe, &dd); if (rc < 0) { /* XXX set an error here */ return -1; } char *msync_end = (char *)dd + sizeof(*dd); msync(msync_start, msync_end - msync_start, MS_SYNC); #warning this is not done yet. //struct section_header *sh = __get_last_section(pe); size_t dd_size = sizeof (*dd) / sizeof (dd->exports); data_dirent *dde = &dd->exports; for (unsigned int i = 0; i < dd_size; i++, dde++) { if (dde->size != 0) { char *addr = compute_mem_addr(pe, dde->virtual_address); msync(addr, dde->size, MS_SYNC); } } return 0; }
int pe_populatecert(Pe *pe, void *cert, size_t size) { int rc; data_directory *dd = NULL; rc = pe_getdatadir(pe, &dd); if (rc < 0) return rc; if (size != dd->certs.size) return -1; void *addr = compute_mem_addr(pe, dd->certs.virtual_address); if (!addr) return -1; memcpy(addr, cert, size); msync(addr, size, MS_SYNC); return 0; }