Oracle FAQ | Your Portal to the Oracle Knowledge Grid |
![]() |
![]() |
Home -> Community -> Mailing Lists -> Oracle-L -> RE: Are There any way of calling NT OS Commands like print, del e
On Thu, 5 Dec 2002, Bishop Lewis wrote:
> Shiva,
>
> Attached is an email from Ankur Shah from another posting - have not tried
> it myself but this may help.
>
> Lewis Bishop
> ---
The email was instructional but it's only good for Unix. There is no equivalent for 'system()' in the Win32 world unless you write your own. The code below has been tested and it works. ;)
WARNING ******* WARNING ***** The code below will work....but it is not secure in that it only does what it is told to do. If somebody sends the proc a disk 'format' command it will run it...you have been warned. Make sure the PL/SQL wrapper procedure that calls the external is SECURE. Also think about running the external procedure listener under a different user id that can't do any damage.
The following code can be placed in a DLL
strcpy(script,cmd); getcwd(cwd,255); cwd[255] = '\0'; // // run the script // Set up the STARTUPINFO Structure...this structure // determines what the window is going to look like lpProcessInfo.dwProcessId = -1; lpProcessInfo.dwProcessId = -1; lpStartupInfo.cb = sizeof(STARTUPINFO); // struct size lpStartupInfo.lpReserved = NULL; // Reserved for Bill lpStartupInfo.lpDesktop = NULL; // WinNT Desktop lpStartupInfo.lpTitle = NULL; // for GUI processes lpStartupInfo.dwX = 0; lpStartupInfo.dwY = 0; lpStartupInfo.dwXSize = 800; lpStartupInfo.dwYSize = 600; lpStartupInfo.wShowWindow = SW_SHOW; lpStartupInfo.cb = 0; // Reserved must be zero lpStartupInfo.lpReserved2 = NULL; // Reserved must be NULL // Call ::CreateProcess to create a new thread....Info about // the new thread will be returned in the PROCESS_INFORMATION // structure lpStartupInfo.dwFlags = STARTF_USESHOWWINDOW | STARTF_USEPOSITION | STARTF_USESIZE; //MessageBox(NULL,script,NULL,MB_OK); if((pid = ::CreateProcess(NULL, // Application Name (executable or bat file) (char *) script, // command Line NULL, // Process Security Attributes NULL, // Thread Security Attributes TRUE, // Handle Inheritance Flag CREATE_SUSPENDED, // Creation Flags NULL, // Process Environment (use Parent's) cwd, // Current directory (use DLL's dir) &lpStartupInfo, // Start up information &lpProcessInfo)) == 0) { Derr = GetLastError(); sprintf(buf," Unable to start process <%s> ErrorCode = %d",
str,Derr);
//MessageBox(NULL,buf,"ERROR",MB_OK); } else { sprintf(msg,"Created Pid %08x",lpProcessInfo.dwProcessId); //MessageBox(NULL,msg,NULL,MB_OK); // // The Thread was created suspended...now we // activiate it. ::ResumeThread(lpProcessInfo.hThread); }
Notes.......
extern "C" ORACMD_API void RunCommand(char *);
in the exported function declarion section of the oracmd.h Also make sure you include direct.h (for getcwd()) and good old stdio.h for the strcpy()/sprintf() calls
4) Compile/build the .dll and copy it to a location that is in
the server's PATH (%SYSTEMROOT%\System32 or %ORACLE_HOME%\bin)
5) Issue the CREATE LIBRARY command pointing at the DLL location
and issue the CREATE PROCEDURE AS EXTERNAL command using the name from the code above i.e. RunCommand
6) Test execution of the procedure.
The process runs in the current directory of the DLL The only way to make sure that it is working is to create a test '.bat' file which will do something fairly harmless and that also logs information to disk. Then you can look for the logfile. Do not put a 'pause' statement in the .bat file or you will be left with orphaned CMD.EXE processes...I know this from experience =8-0
Also....don't try to redirect the stdout/stderr of the batfile through the DLL invocation. It won't work :( I fooled around for a while with command line parsing and opening/inheriting file handles from the CreateProcess API but I could not get it working. Anything that tries to use a GUI will also cause it to crash since there's no Desktop window handle.
Oh....and whatever you do, don't pass a command buffer larger than 1K (1024 bytes)...you'll notice the hard-coded values. It will crash for sure.
Via con Dios/Caveat Emptor
Jeff Herrick
ps....if you want the .DLL binary (ie you don't have a Visual C++
compiler) then email me off-list for a copy.
-- Please see the official ORACLE-L FAQ: http://www.orafaq.com -- Author: Jeff Herrick INET: jherrick_at_igs.net 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: ListGuru_at_fatcity.com (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).Received on Thu Dec 05 2002 - 15:54:17 CST
![]() |
![]() |