We often need to refresh test and development databases with exports that
have extent sizing a lot bigger that what we want.  In test and ESPECIALLY
dev, space and file system availability often require us to just  get
something working without regard for performance.  In these cases, extent
sizing in the exports often prevents us from loading even a row-less import
into the test/dev database.  The following C program was written to deal
with those situations.  I have used it enough that I think I can go ahead
and toss it out to the world.  The program is functional but not necessarily
elegant.  Of course, no guarantees about anything are made.  If you make any
improvements, I would be most appreciative if you sent them.

====== SNIP ====== SNIP ====== SNIP ====== SNIP ====== SNIP ====== SNIP
======

/***************************************************************
** This was hastily written by Stephen Lee because we've      **
** been needing something like this real bad for a while.     **
** If you leave the section that opens the files commented,   **
** then the syntax would be something like:                   **
** modify_extents < dumpfile > modified_dump_file             **
**                                                            **
** Even though this has been tested against enough exports    **
** that it seems to work OK, I do have some nagging doubts    **
** about how universally compatible it is.  I do make some    **
** assumptions about the text in an export dump file and      **
** about the size of a character in that file.                **
**                                                            **
** This program changes the INITIAL and NEXT extent size      **
** specification in the dump file to a fixed size.  You can   **
** edit this value in the program, prior to compiling it.     **
**                                                            **
** It is acknowledged that this is a rather bare-bones        **
** program, but it needed to written in a hurry.  Enhancement **
** of the program is left as an exercise for the reader.      **
***************************************************************/

#include <sys/types.h>
#include <sys/stat.h>
#include <sys/param.h>
#include <sys/signal.h>
#include <sys/fault.h>
#include <sys/syscall.h>
#include <sys/procfs.h>
#include <dirent.h>
#include <fcntl.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <pwd.h>
#include <math.h>
#include <time.h>
#include <termios.h>
#include <signal.h>
#include <ctype.h>
#include <netdb.h>
/** Include the kitchen sink too **/

/***************** BEGIN MAIN ******************/

int main (int argc, char **argv, char **envp) {

        int in, out, bytes_read, diddle, match = 0, create = 0;
        char read_buf[57344], write_buf[65536], diddler;

        // Note that the following strings contain a space. That is
important.
        char *s0 = "CREATE ";
        char *s1 = "ALTER ";
        char *s8 = "INITIAL ";
        char *s9 = "NEXT ";
        int s0_len = strlen(s0);
        int s1_len = strlen(s1);
        int s8_len = strlen(s8);
        int s9_len = strlen(s9);
        int i, j0, j1, j8, j9, x, skip = 0;

/***************************************************************************
****
** Un-comment this section and use the open statements if you want to
hard-code
** the paths, or if you want to use something like argv[1] and argv[2].

        if( (in = open("/export/oracle/admin/FTLP/exp/test.dmp", O_RDONLY))
< 0 ) {
                printf("\nFailed to open input file.\n");
                return 1;
        }

        if( (out = open("/export/oracle/admin/FTLP/exp/modified.dmp",
O_RDWR|O_CREAT|O_TRUNC)) < 0 ) {
                printf("\nFailed to open output file.\n");
                return 1;
        }
        fchmod(out, 0600);

****************************************************************************
/

/***** Use the dup commands if you want to use command-line redirection as
in:
 ***** program_name < input_file > output_file ***/
        in = dup(0);
        out = dup(1);

/**
 ** The following loop reads bytes from the input file and copies them to
the output file.
 ** While it is doing this, it is looking for matches to the strings defined
in s0, s1, etc.
 ** S0 and s1 define when we have found the beginning of a CREATE or ALTER
command and
 ** should start looking for the strings INITIAL and NEXT.  When those
strings are found,
 ** and we verify that they are followed by a number, then the numeric data
is replaced by
 ** the new characters.  Then any following numeric data is skipped until we
get to the
 ** next space.  We write the output buffer every time we read a new input
buffer.
 ** We continue this until the entire input file has been read.
 ** The reason for the CREATE and ALTER searches is to throw in a quart or
two of paranoia.
 ** This requires that both strings CREATE/ALTER and INITIAL/NEXT to be
present.  I suppose
 ** there some chance that we could have these strings present, but the line
NOT be a line
 ** that should be modified.  But I think the chance is so small as to be
insignificant.
**/

        diddle = j0 = j1 = j8 = j9 = x = 0;
        diddler = 124;
        fprintf(stderr,"%c",124);
        while( (bytes_read = read(in,read_buf,49152)) > 0 ) {
                for( i = 0; i < bytes_read; ++i ) {
                        // If we have a newline or carriage return, then
reset all string searches.
                        if( (read_buf[i] == 10) || (read_buf[i] == 13) ) {
j0 = j1 = j8 = j9 = create = skip = match = 0; }
                        // When we are skipping numeric data.
                        if( (skip == 1) && (read_buf[i] != 32) ) continue;
                        // When we were skipping numeric data and have found
the next space.
                        if( (skip == 1) && (read_buf[i] == 32) ) skip = 0;

                        // If we found INITIAL or NEXT and it is followed by
a number, make the substitution.
                        if( (match == 1) && (read_buf[i] > 47) &&
(read_buf[i] < 58) ) {
                                write_buf[x++] = '2';
                                write_buf[x++] = 'M';
                                j8 = j9 = match = 0;
                                skip = 1;
                                continue;
                        }
                        else match = 0;

                        // Copy input buffer to output buffer
                        write_buf[x++] = read_buf[i];

                        // Look for CREATE or ALTER
                        if( read_buf[i] == s0[j0] ) ++j0; else j0 = 0;
                        if( read_buf[i] == s1[j1] ) ++j1; else j1 = 0;
                        if( (j0 == s0_len) || (j1 == s1_len) ) { create = 1;
continue; }
                        if( create == 0 ) continue;

                        // Look for INITIAL or NEXT
                        if( read_buf[i] == s8[j8] ) ++j8; else j8 = 0;
                        if( read_buf[i] == s9[j9] ) ++j9; else j9 = 0;
                        if( (j8 == s8_len) || (j9 == s9_len) ) match = 1;
                }
                write(out,write_buf,x+0);
                if( diddle == 50 ) {
                        if( diddler == 124 ) { fprintf(stderr,"%c%c",8,47);
diddler = 47; }
                        else if( diddler == 47 ) { fprintf(stderr,
"%c%c",8,45); diddler = 45; }
                        else if( diddler == 45 ) { fprintf(stderr,
"%c%c",8,92); diddler = 92; }
                        else if( diddler == 92 ) { fprintf(stderr,
"%c%c",8,124); diddler = 124; }
                        diddle = 0;
                }
                ++diddle;
                x = 0;
        }
        fprintf(stderr,"\n");

/** If you have used open function and want to be clean and tidy.
        close(in);
        close(out);
**/

        return 0;
        
}

/***************** END MAIN ******************/
-- 
Please see the official ORACLE-L FAQ: http://www.orafaq.com
-- 
Author: Stephen Lee
  INET: [EMAIL PROTECTED]

Fat City Network Services    -- 858-538-5051 http://www.fatcity.com
San Diego, California        -- Mailing list and web hosting services
---------------------------------------------------------------------
To REMOVE yourself from this mailing list, send an E-Mail message
to: [EMAIL PROTECTED] (note EXACT spelling of 'ListGuru') and in
the message BODY, include a line containing: UNSUB ORACLE-L
(or the name of mailing list you want to be removed from).  You may
also send the HELP command for other information (like subscribing).

Reply via email to