summaryrefslogtreecommitdiff
path: root/gcc/gcov-io.c
diff options
context:
space:
mode:
authortejohnson <tejohnson@138bc75d-0d04-0410-961f-82ee72b054a4>2014-01-08 16:37:08 +0000
committertejohnson <tejohnson@138bc75d-0d04-0410-961f-82ee72b054a4>2014-01-08 16:37:08 +0000
commit677451260eabdf47945c73753134053b8f417755 (patch)
treefffc9c28e27be439d23aa1e73163256e25cf97f7 /gcc/gcov-io.c
parent6db33a3dc3c8a1f5570d37eebac1ebe2ea260a66 (diff)
downloadgcc-677451260eabdf47945c73753134053b8f417755.tar.gz
2014-01-08 Rong Xu <xur@google.com>
* gcc/gcov-io.c (gcov_var): Move from gcov-io.h. (gcov_position): Ditto. (gcov_is_error): Ditto. (gcov_rewrite): Ditto. * gcc/gcov-io.h: Refactor. Move gcov_var to gcov-io.h, and libgcov only part to libgcc/libgcov.h. * libgcc/libgcov-driver.c: Use libgcov.h. (buffer_fn_data): Use xmalloc instead of malloc. (gcov_exit_merge_gcda): Ditto. * libgcc/libgcov-driver-system.c (allocate_filename_struct): Ditto. * libgcc/libgcov.h: New common header files for libgcov-*.h. * libgcc/libgcov-interface.c: Use libgcov.h * libgcc/libgcov-merge.c: Ditto. * libgcc/libgcov-profiler.c: Ditto. * libgcc/Makefile.in: Add dependence to libgcov.h git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@206435 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/gcov-io.c')
-rw-r--r--gcc/gcov-io.c55
1 files changed, 55 insertions, 0 deletions
diff --git a/gcc/gcov-io.c b/gcc/gcov-io.c
index ef5120a0c1f..b710f596e37 100644
--- a/gcc/gcov-io.c
+++ b/gcc/gcov-io.c
@@ -36,6 +36,61 @@ static const gcov_unsigned_t *gcov_read_words (unsigned);
static void gcov_allocate (unsigned);
#endif
+/* Optimum number of gcov_unsigned_t's read from or written to disk. */
+#define GCOV_BLOCK_SIZE (1 << 10)
+
+GCOV_LINKAGE struct gcov_var
+{
+ FILE *file;
+ gcov_position_t start; /* Position of first byte of block */
+ unsigned offset; /* Read/write position within the block. */
+ unsigned length; /* Read limit in the block. */
+ unsigned overread; /* Number of words overread. */
+ int error; /* < 0 overflow, > 0 disk error. */
+ int mode; /* < 0 writing, > 0 reading */
+#if IN_LIBGCOV
+ /* Holds one block plus 4 bytes, thus all coverage reads & writes
+ fit within this buffer and we always can transfer GCOV_BLOCK_SIZE
+ to and from the disk. libgcov never backtracks and only writes 4
+ or 8 byte objects. */
+ gcov_unsigned_t buffer[GCOV_BLOCK_SIZE + 1];
+#else
+ int endian; /* Swap endianness. */
+ /* Holds a variable length block, as the compiler can write
+ strings and needs to backtrack. */
+ size_t alloc;
+ gcov_unsigned_t *buffer;
+#endif
+} gcov_var;
+
+/* Save the current position in the gcov file. */
+static inline gcov_position_t
+gcov_position (void)
+{
+ gcc_assert (gcov_var.mode > 0);
+ return gcov_var.start + gcov_var.offset;
+}
+
+/* Return nonzero if the error flag is set. */
+static inline int
+gcov_is_error (void)
+{
+ return gcov_var.file ? gcov_var.error : 1;
+}
+
+#if IN_LIBGCOV
+/* Move to beginning of file and initialize for writing. */
+GCOV_LINKAGE inline void
+gcov_rewrite (void)
+{
+ gcc_assert (gcov_var.mode > 0);
+ gcov_var.mode = -1;
+ gcov_var.start = 0;
+ gcov_var.offset = 0;
+ fseek (gcov_var.file, 0L, SEEK_SET);
+}
+#endif
+
static inline gcov_unsigned_t from_file (gcov_unsigned_t value)
{
#if !IN_LIBGCOV