/* * Copyright (C) 2016 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ #include #include #include #include #include #include #include #include void *reallocOrDie(void *buf, size_t bufSz) { void *newBuf = realloc(buf, bufSz); if (!newBuf) { fprintf(stderr, "Failed to allocate %zu bytes\n", bufSz); exit(2); } return newBuf; } void assertMem(size_t used, size_t total) { if (used <= total) return; fprintf(stderr, "Buffer size %zu is not big enough to complete operation; we need %zu bytes\n", total, used); exit(2); } // read file of known size, make sure the size is correct bool readFile(void *dst, uint32_t len, const char *fileName) { FILE *f = fopen(fileName, "rb"); bool ret = false; if (!f) return false; if (len != fread(dst, 1, len, f)) goto out; if (fread(&len, 1, 1, f)) //make sure file is actually over goto out; ret = true; out: fclose(f); return ret; } // read complete file of unknown size, return malloced buffer and size void *loadFile(const char *fileName, uint32_t *size) { FILE *f = fopen(fileName, "rb"); uint8_t *dst = NULL; uint32_t len = 0, grow = 16384, total = 0; uint32_t block; if (!f) { fprintf(stderr, "couldn't open %s: %s\n", fileName, strerror(errno)); exit(2); } do { len += grow; dst = reallocOrDie(dst, len); block = fread(dst + total, 1, grow, f); total += block; } while (block == grow); *size = total; if (!feof(f)) { fprintf(stderr, "Failed to read entire file %s: %s\n", fileName, strerror(errno)); free(dst); fclose(f); dst = NULL; exit(2); } fclose(f); return dst; } static void doPrintHash(FILE *out, const char *pfx, const uint32_t *hash, size_t size, int increment) { size_t i; int pos; fprintf(out, "%s: ", pfx); for (i = 0, pos = 0; i < size; ++i, pos += increment) fprintf(out, "%08" PRIx32, hash[pos]); fprintf(out, "\n"); } void printHash(FILE *out, const char *pfx, const uint32_t *hash, size_t size) { doPrintHash(out, pfx, hash, size, 1); } void printHashRev(FILE *out, const char *pfx, const uint32_t *hash, size_t size) { doPrintHash(out, pfx, hash + size - 1, size, -1); }