+++ /dev/null
-/***
- fusefile-merge - merge a fusefile overlay into its underling
-
- Copyright (C) 2023- Ralph Ronnquist
-
- This program is free software: you can redistribute it and/or
- modify it under the terms of the GNU General Public License as
- published by the Free Software Foundation, either version 3 of the
- License, or (at your option) any later version.
-
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with this program. If not, see
- <http://www.gnu.org/licenses/>.
-*/
-
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <time.h>
-#include <errno.h>
-#include <sys/types.h>
-#include <sys/stat.h>
-#include <fcntl.h>
-#include <sys/mman.h>
-
-/**
- * An overlay file consists of a data block followed by a count of
- * struct Region elements plus that many elements.
- */
-struct Region {
- off_t beg;
- off_t end;
-};
-
-/**
- * Table head
- */
-struct Table {
- size_t count;
- struct Region regions[];
-};
-
-struct FileInfo {
- char *name;
- size_t size;
-};
-
-struct FileInfo basefile, olyfile;
-
-/**
- *
- */
-static struct Table *loadtable() {
- if ( basefile.size >= olyfile.size ) {
-#if DEBUG
- fprintf( stderr, "basefile.size >= olyfile.size\n" );
-#endif
- return 0;
- }
- size_t tbl = ( olyfile.size - basefile.size );
- if ( ( tbl % sizeof( off_t ) ) != 0 ) {
-#if DEBUG
- fprintf( stderr, "( tbl %% sizeof( off_t ) ) != 0\n" );
-#endif
- return 0;
- }
- size_t count = tbl / sizeof( off_t );
- if ( ( count & 1 ) == 0 ) { // Needs an odd number of off_t values
-#if DEBUG
- fprintf( stderr, "( count & 1 ) == 0\n" );
-#endif
- return 0;
- }
- count = ( count - 1 ) / 2;
- int fd = open( olyfile.name, O_RDONLY );
- if ( fd < 0 ) {
- perror( olyfile.name );
- return 0;
- }
- struct Table *ptr =
- mmap( 0, tbl, PROT_READ, MAP_PRIVATE, fd, basefile.size );
- return ( ptr->count != count )? 0 : ptr;
-}
-
-static void usage() {
- fprintf( stderr, "Usage: basefile overlayfile\n" );
- exit( 1 );
-}
-
-/**
- * Application entry. This program dumps the overlay table as a
- * fusefile fragments sequence, with newline?
- */
-int main(int argc,char **argv) {
- static struct stat info;
-
- if ( argc != 3 ) {
- usage();
- }
- basefile.name = argv[1];
- if ( stat( basefile.name, &info ) ) {
- perror( basefile.name );
- exit( 1 );
- }
- basefile.size = info.st_size;
-
- olyfile.name = argv[2];
- if ( stat( olyfile.name, &info ) ) {
- perror( olyfile.name );
- exit( 1 );
- }
- olyfile.size = info.st_size;
-
- struct Table *table = loadtable();
- if ( table == 0 ) {
- fprintf( stderr, "%s is not onverlay for %s\n",
- olyfile.name, basefile.name );
- fprintf( stderr, " %s: %ld\n", basefile.name, basefile.size );
- fprintf( stderr, " %s: %ld\n", olyfile.name, olyfile.size );
- exit( 1 );
- }
- int i;
- size_t pos = 0;
- for ( i = 0; i < table->count; i++ ) {
- struct Region *r = &(table->regions[i]);
- if ( pos < r->beg ) {
- fprintf( stdout, "%s/%ld:%ld\n", basefile.name, pos, r->beg );
- }
- fprintf( stdout, "%s/%ld:%ld\n", olyfile.name, r->beg, r->end );
- pos = r->end;
- }
- if ( pos < basefile.size ) {
- fprintf( stdout, "%s/%ld:%ld\n", basefile.name, pos, basefile.size );
- }
- return( 0 );
-}