/* ********************************************************************* */ /* * * */ /* * Copyright (c) 2006-2010, Dirk Krause * */ /* * All rights reserved. * */ /* * * */ /* * Redistribution and use in source and binary forms, * */ /* * with or without modification, are permitted provided * */ /* * that the following conditions are met: * */ /* * * */ /* * * Redistributions of source code must retain the above * */ /* * copyright notice, this list of conditions and the * */ /* * following disclaimer. * */ /* * * Redistributions in binary form must reproduce the above * */ /* * opyright notice, this list of conditions and the following * */ /* * disclaimer in the documentation and/or other materials * */ /* * provided with the distribution. * */ /* * * Neither the name of the Dirk Krause nor the names of * */ /* * contributors may be used to endorse or promote * */ /* * products derived from this software without specific * */ /* * prior written permission. * */ /* * * */ /* * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND * */ /* * CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, * */ /* * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF * */ /* * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * */ /* * DISCLAIMED. * */ /* * IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE * */ /* * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * */ /* * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT * */ /* * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; * */ /* * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * */ /* * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN * */ /* * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE * */ /* * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * */ /* * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH * */ /* * DAMAGE. * */ /* * * */ /* ********************************************************************* */ #line 36 "blksize.ctr" /** @file blksize.c Block size corrector. */ #include #include #if DK_HAVE_STDLIB_H #include #endif #if DK_HAVE_UNISTD_H #include #endif #if DK_HAVE_PROCESS_H #include #endif #if DK_HAVE_ERRNO_H #include #endif #include #include #line 64 "blksize.ctr" /** Exit status code. */ static int exval = 0; /** Input buffer. */ static char ibuffer[16384]; /** Default output buffer. */ static char obuffer[16384]; /** Allocated output buffer. */ static char *allocated_buffer = NULL; /** Pointer to output buffer. */ static char *ob = obuffer; /** Block size to enforce. */ static size_t block_size = 512; /** Number of used bytes in output buffer. */ static size_t ob_used = 0; /** Flush output buffer. */ static void flush_output DK_P0() { dk_read_write_t bytes_written = 0; if(ob_used) { bytes_written = write(1, ob, ob_used); if(bytes_written != ob_used) { fprintf( stderr, "Write problem!\nBytes to write: %lu\nBytes written: %lu\n", (unsigned long)ob_used, (unsigned long)bytes_written ); fflush(stderr); } } ob_used = 0; } /** Put one byte to output buffer, flush if necessary. @param c Character to put. */ static void put_output_char DK_P1(char ,c) { ob[ob_used++] = c; if(ob_used >= block_size) { flush_output(); } } /** The blksize programs main() function. @param argc Number of command line arguments. @param argv Command line arguments array. @return 0 on success, any other value indicates an error. */ #if DK_HAVE_PROTOTYPES int main(int argc, char *argv[]) #else main(argc, argv) int argc; char *argv[]; #endif { unsigned long ul; char *ptr; dk_read_write_t bytes_read, i; int cc; int old_stdin_binary = 0, old_stdout_binary = 0; if(argc > 1) { if(sscanf(argv[1], "%lu", &ul) == 1) { block_size = (size_t)ul; } else { fprintf( stderr, "Usage:\n------\nblksize []\n" ); fflush(stderr); exit(0); } } old_stdin_binary = dksf_fdesk_binary(0, 1); old_stdout_binary = dksf_fdesk_binary(1, 1); if(block_size > 16384) { allocated_buffer = dk_new(char,block_size); if(allocated_buffer) { ob = allocated_buffer; } else { block_size = 16384; fprintf( stderr, "blksize: ERROR: Failed to allocate large buffer!\n" ); fprintf( stderr, "Switching blocksize down to 16384.\n" ); fflush(stderr); exval = 1; } } cc = 1; ob_used = 0; while(cc) { bytes_read = read(0, ibuffer, sizeof(ibuffer)); if(bytes_read > 0) { ptr = ibuffer; i = 0; while(i++ < bytes_read) { put_output_char(*(ptr++)); } } else { cc = 0; /* finished or error */ if(bytes_read < 0) { fprintf( stderr, "Read problem, return code = %d, errno = %d\n", (int)bytes_read, errno ); fflush(stderr); } } } flush_output(); (void)dksf_fdesk_binary(1, old_stdout_binary); (void)dksf_fdesk_binary(0, old_stdin_binary); if(allocated_buffer) { dk_delete(allocated_buffer); allocated_buffer = NULL; } exit(exval); return exval; }