以下の3つのサンプル プログラム ファイルがFastExportユーティリティに付属しています。これらのファイルは、ワークステーション接続のWindowsクライアント システムにおいて、INMOD、OUTMOD、および通知出口ルーチンを生成し、FastExportジョブ スクリプトの中で使用するのに役立ちます。これらのサンプル ファイルのリストは、このトピックの後半で説明します。
サンプル ファイル | 説明 |
---|---|
feimod.c | INMODルーチンのソース ファイルです。 |
feomod.c | OUTMODルーチンのソース ファイルです。 |
fenotf.c | 通知出口ルーチンのソース ファイルです。 |
FastExportジョブでINMOD、OUTMOD、または通知出口ルーチンを生成して使用する方法
INMODルーチン、OUTMODルーチン、または通知出口ルーチンを生成して使用するためには、参考用サンプル ファイル リストを参照し、この手順に従います。
- ルーチンのソース ファイルを編集し、dynamn名が__declspecであることを確かめます。
- このトピックの後半の以下のサンプル ルーチン ファイルのリストを参照してください。
- feimod.c
- feomod.c
- fenotf.c
- 以下のコマンドを使って、DDLを作成します。
cl.exe /nologo /MTd /W3 /Zp1 /c /O2 -D _WINDOWS -D _MBCS -D _USRDLL -D _CRT_SECURE_NO_DEPRECATE -D WIN64 -D _WIN64 -D WIN32 -D TA_nt_x8664=1 /Fo sourcefilename.obj sourcefilename.c
link.exe -largeaddressaware -incremental:no -debug -nologo /machine:X64 -dll -subsystem:windows,5.02 /out:sourcefilename.dll sourcefilename.obj
ここで、sourcefilenameはINMODまたは通知出口ルーチンのソース ファイルの名前です。
コマンドの実行が成功すると、ソース ファイルと同じ名前にファイル拡張子.dllが付いた次のようなファイルが生成されます。
sourcefilename.dll
- FastExportジョブ スクリプトの中で、以下のようにsourcefilename.dllを使用します。
ルーチンのタイプ sourcefilename.dllファイルの指定方法 INMOD IMPORTコマンドのINMOD modulename OUTMOD EXPORTコマンドのOUTMOD modulename 通知出口 BEGIN EXPORTコマンドのNOTIFYオプションのEXIT name指定
サンプルINMODルーチン
以下に挙げるのは、FastExportユーティリティ ソフトウェアに付属のサンプルINMODルーチンfeimod.cのリストです。
#include <stdio.h> #include <stdlib.h> /**********************************************************************/ /* */ /* feimod.c - Sample Inmod for FastExport. */ /* */ /* Copyright1996-2007, 2016 by Teradata Corporation. */ /* All Rights Reserved. */ /* TERADATA CONFIDENTIAL AND TRADE SECRET */ /* */ /* Purpose - This inmod generates two integers per record. The */ /* first is even and the second number is odd. */ /* */ /* Note - The number of records per file is determined by the */ /* variable NUM_RECORDS */ /* */ /* Execute - Build Inmod on a Unix system */ /* compile and link into shared object */ /* cc -G feimod.c - o feimod.so */ /* */ /* - Build Inmod on a Win32 system */ /* compile and link into dynamic link library */ /* cl /DWIN32 /LD feimod.c */ /* */ /**********************************************************************/ static int msg_cnt = 0; typedef struct { int ioseq; short len; char param[2000]; } param_type; /* This structure is used to pass an odd and an even integer */ /* back to multiload */ typedef struct { int code; int len; char data[32768]; } data_type; #ifdef WIN32 /* Change for WIN32 */ __declspec(dllexport) void _dynamn(data_type *data_buf , param_type *parm_buf) #else void _dynamn(data_buf, parm_buf) data_type *data_buf; param_type *parm_buf; #endif { char *myptr; int i; static int RECNUM = 0; /* number of records to load */ static int odd_counter = 0; /* odd integer counter */ static int even_counter = 0; /* even integer counter */ #ifdef DEBUG printf("\n"); printf("jmod2: on input:\n"); printf("jmod2: message code: %d\n", data_buf->code); printf("jmod2: data bytes: %d\n", data_buf->len); if (data_buf->len) printf("jmod2: data: *%s*\n", data_buf->data); printf("jmod2: param ioseq: %d\n", parm_buf->ioseq); printf("jmod2: param bytes: %d\n", parm_buf->len); if (parm_buf->len) printf("jmod2: param str: %s\n", parm_buf->param); printf("jmod2: message cnt: %d\n", ++msg_cnt); #endif switch (data_buf->code) { case 0: printf("jmod2: initializing and returning 1st record:\n"); RECNUM = 6; printf("jmod2: Records requested = %ld\n", RECNUM); if ( RECNUM <= 0 ) { printf("jmod2: numbers of records is <= 0 [%ld]\n", RECNUM); } /* initialize the counters */ odd_counter = 1; even_counter = 2; /* copy the counters to the data buffer */ myptr = (char *) &odd_counter; for (i=0; i<4; ++i, ++myptr) { data_buf->data[i] = *myptr; } myptr = (char *) &even_counter; for (i=4; i<8; ++i, ++myptr) { data_buf->data[i] = *myptr; } /* go to next values and increment the counters */ odd_counter += 2; even_counter +=2; --RECNUM; /* return the results */ data_buf->code = 0; data_buf->len = 8; break; case 1: #ifdef DEBUG printf("jmod2: returning a record:\n"); #endif if (RECNUM) { /* copy the counters to the data buffer */ myptr = (char *) &odd_counter; for (i=0; i<4; ++i, ++myptr) { data_buf->data[i] = *myptr; } myptr = (char *) &even_counter; for (i=4; i<8; ++i, ++myptr) { data_buf->data[i] = *myptr; } /* increment to next values and decrement record counter */ odd_counter += 2; even_counter += 2; --RECNUM; /* return the results */ data_buf->code = 0; data_buf->len = 8; break; } else { /* done sending records, return non-zero result */ printf("jmod2: all records sent\n"); data_buf->code = 1; break; } case 2: printf("jmod2: repositioning to last checkpoint (HOST)\n"); data_buf->code = 0; data_buf->len = 0; break; case 3: printf("jmod2: taking a checkpoint\n"); data_buf->code = 0; data_buf->len = 0; break; case 4: printf("jmod2: repositioning to last checkpoint (DBC)\n"); data_buf->code = 0; data_buf->len = 0; break; case 5: printf("jmod2: terminating:\n"); data_buf->code = 0; data_buf->len = 0; break; case 6: printf("jmod2: initializing and receiving 1st record:\n"); data_buf->data[1] = '%'; data_buf->code = 0; break; case 7: printf("jmod2: receiving a record:\n"); data_buf->data[1] = '%'; data_buf->code = 0; break; } #ifdef DEBUG printf("jmod2: on output:\n"); printf("jmod2: message code: %d\n", data_buf->code); printf("jmod2: data bytes: %d\n", data_buf->len); if (data_buf->len) printf("jmod2: data: *%s*\n", data_buf->data); printf("\n"); #endif }
サンプルOUTMODルーチン
以下に挙げるのは、FastExportユーティリティ ソフトウェアに付属のサンプルOUTMODルーチンfeomod.cのリストです。
#include <stdio.h> #include <stdlib.h> /**********************************************************************/ /* */ /* feomod.c - Sample Outmod for FastExport. */ /* */ /* Copyright1996-2007, 2016 by Teradata Corporation. */ /* All Rights Reserved. */ /* TERADATA CONFIDENTIAL AND TRADE SECRET */ /* */ /* Purpose - This outmod deletes the data passed to it. */ /* */ /* Execute - Build Outmod on a Unix system */ /* compile and link into shared object */ /* cc -G feomod.c - o feomod.so */ /* */ /* - Build Outmod on a Win32 system */ /* compile and link into dynamic link library */ /* cl /DWIN32 /LD feomod.c */ /* */ /* */ /**********************************************************************/ typedef unsigned short Int16; typedef unsigned char Int8; typedef unsigned int UInt32; #ifdef WIN32 /* Change for WIN32 */ __declspec(dllexport) UInt32 _dynamn( int *code, int *stmno, int *InLen, char *InBuf, int *OutLen, char *OutBuf ) #else UInt32 _dynamn(code, stmno, InLen, InBuf, OutLen, OutBuf) int *code; int *stmno; int *InLen; char *InBuf; int *OutLen; char *OutBuf; #endif { /* case on entry code */ switch (*code) { case 1: /* Initialization, no other values */ printf ("OUTMOD Initial Entry\n"); break; case 2: /* Cleanup call, no other values */ printf ("OUTMOD End of Responses Entry\n"); break; case 3: /* Process response record */ *InLen=0; *OutLen=0; break; case 4: /* Checkpoint, no other values */ printf ("OUTMOD Checkpoint Entry\n"); break; case 5: /* DBC restart - close and reopen the output files */ printf ("OUTMOD DBC Restart Entry\n"); break; case 6: /* Host restart */ printf ("OUTMOD Host Restart Entry\n"); break; default: printf ("OUTMOD Invalid Entry code\n"); break; } return (0); }
サンプル通知出口ルーチン
次に、FastExportユーティリティ ソフトウェアに付属するサンプル通知出口ルーチンfenotf.cのリストを示します。
/**********************************************************************/ /* */ /* fenotf.c - Sample Notify Exit for FastExport. */ /* */ /* Copyright1996-2013, 2016 by Teradata Corporation. */ /* All Rights Reserved. */ /* TERADATA CONFIDENTIAL AND TRADE SECRET */ /* */ /* Purpose - This is a sample notify exit for FastExport. */ /* */ /* Execute - Build Notify on a Unix system */ /* compile and link into shared object */ /* cc -G fenotf.c - o fenotf.so */ /* */ /* - Build Notify on a Win32 system */ /* compile and link into dynamic link library */ /* cl /DWIN32 /LD fenotf.c */ /* */ /**********************************************************************/ #include <stdio.h> typedef unsigned int UInt32; typedef int Int32; #define NOTIFYID_FASTLOAD 1 #define NOTIFYID_MULTILOAD 2 #define NOTIFYID_FASTEXPORT 3 #define NOTIFYID_BTEQ 4 #define NOTIFYID_TPUMP 5 #define MAXVERSIONIDLEN 32 #define MAXUTILITYNAMELEN 32 #define MAXUSERNAMELEN 64 #define MAXUSERSTRLEN 80 #define MAXFILENAMELEN 256 #define MAXREQUESTLEN 32000 #define MAXDBNAMELEN 62 #define MAXUINT64 24 typedef enum { NXEventInitialize = 0, NXEventFileInmodOpen = 1, NXEventDBSRestart = 9, NXEventCLIError = 10, NXEventDBSError = 11, NXEventExit = 12, NXEventExportBegin = 31, NXEventReqSubmitBegin = 32, NXEventReqSubmitEnd = 33, NXEventReqFetchBegin = 34, NXEventFileOutmodOpen = 35, NXEventStmtFetchBegin = 36, NXEventStmtFetchEnd = 37, NXEventReqFetchEnd = 38, NXEventExportEnd = 39, NXEventBlockCount = 40, NXEventExportEnd64 = 41, NXEventInitializeEON = 42, NXEventReqSubmitBeginEON = 43, NXEventExportBeginEON = 44 } NfyExpEvent; typedef struct _FXNotifyExitParm { UInt32 Event; union { struct { UInt32 VersionLen; char VersionId[MAXVERSIONIDLEN]; UInt32 UtilityId; UInt32 UtilityNameLen; char UtilityName[MAXUTILITYNAMELEN]; UInt32 UserNameLen; char UserName[MAXUSERNAMELEN]; UInt32 UserStringLen; char UserString[MAXUSERSTRLEN]; }Initialize; struct { UInt32 VersionLen; char VersionId[MAXVERSIONIDLEN]; UInt32 UtilityId; UInt32 UtilityNameLen; char UtilityName[MAXUTILITYNAMELEN]; UInt32 UserNameLen; char *UserName; UInt32 UserStringLen; char UserString[MAXUSERSTRLEN]; } InitializeEON; struct { UInt32 FileNameLen; char FileOrInmodName[MAXFILENAMELEN]; UInt32 dummy; } FileInmodOpen ; struct { UInt32 dummy; } DBSRestart; struct { UInt32 ErrorCode; } CLIError; struct { UInt32 ErrorCode; } DBSError; struct { UInt32 ReturnCode; } Exit; struct { UInt32 dummy; char DatabaseName[MAXDBNAMELEN]; } ExportBegin; struct { UInt32 dummy; char *DatabaseName; } ExportBeginEON; struct { UInt32 RequestLen; char Request[MAXREQUESTLEN]; } ReqSubmitBegin; struct { UInt32 RequestLen; char *Request; } ReqSubmitBeginEON; struct { UInt32 StatementCnt; UInt32 BlockCnt; } ReqSubmitEnd; struct { UInt32 dummy; } ReqFetchBegin; struct { UInt32 FileNameLen; char FileOrOutmodName[MAXFILENAMELEN]; } FileOutmodOpen; struct { UInt32 StatementNo; UInt32 BlockCnt; } StmtFetchBegin; struct { UInt32 Records; } StmtFetchEnd; struct { UInt32 RecsExported; UInt32 RecsRejected; } ReqFetchEnd; struct { UInt32 RecsExported; UInt32 RecsRejected; } ExportEnd; struct { char RecsExported[MAXUINT64]; UInt32 RecsRejected; }ExportEnd64; struct { UInt32 BlockCount; } BlockCount; } Vals; } FXNotifyExitParm; extern Int32 FXNotifyExit( #ifdef __STDC__ FXNotifyExitParm *Parms #endif ); #ifdef WIN32 __declspec(dllexport) Int32 _dynamn(FXNotifyExitParm *P) #else Int32 _dynamn( FXNotifyExitParm *P) #endif { FILE *fp; if (!(fp = fopen("NFYEXIT.OUT", "a"))) return(1); switch(P->Event) { case NXEventInitialize : /* Nothing */ fprintf(fp, "exit called @ fexp init.\n"); fprintf(fp, "Version: %s\n", P->Vals.Initialize.VersionId); fprintf(fp, "Utility: %s\n", P->Vals.Initialize.UtilityName); fprintf(fp, "User: %s\n", P->Vals.Initialize.UserName); if (P->Vals.Initialize.UserStringLen) fprintf(fp, "UserString: %s\n", P->Vals.Initialize.UserString); break; case NXEventInitializeEON : fprintf(fp, "exiteon called @ fexp init.\n"); fprintf(fp, "Version: %s\n", P->Vals.InitializeEON.VersionId); fprintf(fp, "Utility: %s\n", P->Vals.InitializeEON.UtilityName); fprintf(fp, "User: %s\n", P->Vals.InitializeEON.UserName); if (P->Vals.InitializeEON.UserStringLen) fprintf(fp, "UserString: %s\n", P->Vals.InitializeEON.UserString); break; case NXEventFileInmodOpen: fprintf(fp, "exit called @ input file open: %s\n", P->Vals.FileInmodOpen.FileOrInmodName); break; case NXEventDBSRestart : fprintf(fp, "exit called @ RDBMS restart detected\n"); break; case NXEventCLIError : fprintf(fp, "exit called @ CLI error %d\n", P->Vals.CLIError.ErrorCode); break; case NXEventDBSError : fprintf(fp, "exit called @ DBS error %d\n", P->Vals.DBSError.ErrorCode); break; case NXEventExit : fprintf(fp, "exit called @ fexp notify out of scope: return code %d.\n", P->Vals.Exit.ReturnCode); break; case NXEventExportBegin : fprintf(fp, "exit called @ export beginning.\n"); fprintf(fp, "exit called @ export beginning - Database Name : %s\n",P->Vals.ExportBegin.DatabaseName); break; case NXEventExportBeginEON : fprintf(fp, "exiteon called @ export beginning.\n"); fprintf(fp, "exit called @ export beginning - Database Name : %s\n", P->Vals.ExportBeginEON.DatabaseName); break; case NXEventReqSubmitBegin : fprintf(fp, "exit called @ request submitted: '%s'.\n", P->Vals.ReqSubmitBegin.Request); break; case NXEventReqSubmitBeginEON : fprintf(fp, "exiteon called @ request submitted: '%s'.\n", P->Vals.ReqSubmitBeginEON.Request); break; case NXEventReqSubmitEnd : fprintf(fp, "exit called @ request done: %d statement(s), \ %d blocks.\n", P->Vals.ReqSubmitEnd.StatementCnt, P->Vals.ReqSubmitEnd.BlockCnt); break; case NXEventReqFetchBegin : fprintf(fp, "exit called @ request fetch beginning.\n"); break; case NXEventFileOutmodOpen: fprintf(fp, "exit called @ output file open: %s\n", P->Vals.FileOutmodOpen.FileOrOutmodName); break; case NXEventStmtFetchBegin : fprintf(fp, "exit called @ statement fetch beginning: stmt #%d, \ %d blocks.\n", P->Vals.StmtFetchBegin.StatementNo, P->Vals.StmtFetchBegin.BlockCnt); break; case NXEventStmtFetchEnd : fprintf(fp, "exit called @ statement fetch end: %d records.\n", P->Vals.StmtFetchEnd.Records); break; case NXEventReqFetchEnd : fprintf(fp, "exit called @ request fetch ends: \ Records exported: %d, Records rejected: %d\n", P->Vals.ReqFetchEnd.RecsExported, P->Vals.ReqFetchEnd.RecsRejected); break; case NXEventExportEnd : fprintf(fp, "exit called @ export ends: \ Records exported: %d, Records rejected: %d\n", P->Vals.ExportEnd.RecsExported, P->Vals.ExportEnd.RecsRejected); break; case NXEventExportEnd64 : fprintf(fp, "exit64 called @ export ends: \ Records exported: %s, Records rejected: %d\n", P->Vals.ExportEnd64.RecsExported, P->Vals.ExportEnd64.RecsRejected); break; case NXEventBlockCount : fprintf(fp, "exit called @ request done in Nospool mode: %d \ blocks.\n", P->Vals.BlockCount.BlockCount); break; } fclose(fp); return(0); }