command line arguments behavior

Just starting out? Need help? Post your questions and find answers here.
essess
New User
New User
Posts: 9
Joined: Wed Jan 15, 2014 4:07 am

command line arguments behavior

Post by essess »

Hello,
Using this code:

Code: Select all

EnableExplicit
OpenConsole()
PrintN( ProgramFilename() )
Define cnt.i = CountProgramParameters()
While cnt
  PrintN( ProgramParameter() )
  cnt - 1
Wend
Input()
; cmdline arguments:
;   com1 < test.txt
I get different behavior when using the ide to run my program:

Code: Select all

C:\prj\purebasic\rwx\PureBasic_Compilation0.exe
com1
<
test.txt
and when using the command line directly:

Code: Select all

C:\prj\purebasic\rwx\PureBasic_Compilation0.exe
com1
I think this is different because the ide does not launch my program through the shell. Therefore, I lose the ability to use redirection.

Is this intended ?
How would you work around this ?
Last edited by essess on Thu Feb 13, 2014 2:23 pm, edited 1 time in total.
User avatar
em_uk
Enthusiast
Enthusiast
Posts: 366
Joined: Sun Aug 08, 2010 3:32 pm
Location: Manchester UK

Re: command line arguments behavior

Post by em_uk »

Fairly sure you cannot use < in the command line as its used for redirection.

I assume PB uses a createprocess function which is different to launching from the command interpreter.

http://technet.microsoft.com/en-us/libr ... 90982.aspx

"< Reads the command input from a file, instead of reading input from the keyboard."
----

R Tape loading error, 0:1
essess
New User
New User
Posts: 9
Joined: Wed Jan 15, 2014 4:07 am

Re: command line arguments behavior

Post by essess »

Yes, I do not want the literal redirection stuff to show up in the command line - I want it to do redirection - I'm not interested in using '<' (sorry, I forgot to mention that). I'm wondering if this is intended, or did the designer of the ide wish to have it's behavior identical to launching from the commandline ?
em_uk wrote:Fairly sure you cannot use < in the command line as its used for redirection.

I assume PB uses a createprocess function which is different to launching from the command interpreter.

http://technet.microsoft.com/en-us/libr ... 90982.aspx

"< Reads the command input from a file, instead of reading input from the keyboard."
JHPJHP
Addict
Addict
Posts: 2285
Joined: Sat Oct 09, 2010 3:47 am

Re: command line arguments behavior

Post by JHPJHP »

I'm wondering if this is intended, or did the designer of the ide wish to have it's behavior identical to launching from the commandline
- PureBasic's OpenConsole works just like Window's API commands; working as intended

... And welcome to the PureBasic Community.
Last edited by JHPJHP on Mon Feb 17, 2014 12:41 am, edited 1 time in total.
essess
New User
New User
Posts: 9
Joined: Wed Jan 15, 2014 4:07 am

Re: command line arguments behavior

Post by essess »

I have no problem with OpenConsole.

My problem is with redirection and how it's interpreted different from the command line (expected) vs. from the ide (unexpected). Is this intended behavior ? To phrase it more directly: I cannot use redirection when launching from the ide, right ?

If I am allowed to use redirection when launching from the ide, I need to file a bug, or figure out what I'm doing wrong. Maybe making a mention of it in the documentation is enough. This was an unexpected result for me and I didn't find the answer in the documentation.

Thank you for the welcome! I don't think that has ever happened to me :D I'll look into your package right now.
User avatar
TI-994A
Addict
Addict
Posts: 2791
Joined: Sat Feb 19, 2011 3:47 am
Location: Singapore
Contact:

Re: command line arguments behavior

Post by TI-994A »

Hi essess. I'm not really sure what you're looking for, but, if I'm not wrong, printing output to the console window does not actually execute any commands. The console window is simply a CUI for program text output, and not the operating systems' command processor. The results that you're getting are simply echoes, and not executions.

To run a program, you'd have to use PureBasic's RunProgram() function:

Code: Select all

RunProgram("calc.exe")
RunProgram("notepad.exe", "someFile.txt", "c:\")   ;someFile.txt should be in c:\
However, to execute command line instructions, you'd have to run the command processor itself, and then pass those instructions as parameters:

Code: Select all

;the /k directive keeps the command prompt alive after execution
RunProgram("cmd", "/k dir", "c:\")
The same goes for redirection operators; since they are functions of the command processor, they can only be invoked through it:

Code: Select all

;the /c directive kills the command prompt upon completion
RunProgram("cmd", "/c dir > cDirFile.txt", "c:\")
The following short example demonstrates how the same is achieved with program output, and also illustrates the dangers of recursive program execution if not properly structured. If your original example had worked, it would have recursively executed itself in an endless loop:

Code: Select all

OpenConsole()
PrintN(ProgramFilename())
p.s = ProgramParameter()
If p = "": p = "1": EndIf
ConsoleTitle("Call #" + p)

PrintN("Select:" + #CRLF$ + "1. to demonstrate recursive execution" +
                   #CRLF$ + "2. to test output redirection" +
                   #CRLF$ + "3. to test input & output redirection" +       
                   #CRLF$ + "0. to terminate")
run.s = Input()
Select Val(run)
  Case 1
    p = Str(Val(p) + 1)
    PrintN("Notice the incremental count in the console title...")
    RunProgram("c:\console.exe", p, "")
  Case 2
    PrintN("Program output saved to file c:\outputFile.txt")
    PrintN("Any key to terminate...")
    RunProgram("cmd", "/c c:\console.exe > c:\outputFile.txt", "")
  Case 3
    PrintN("sort utility received input from c:\unsortedFile.txt" + 
           #CRLF$ + "and saved output to c:\sortedFile.txt")
    PrintN("Any key to terminate...")
    RunProgram("cmd", "/c sort < c:\unsortedFile.txt > c:\sortedFile.txt", "")
    Input()
EndSelect

CloseConsole()
It also works directly from the IDE, but the program name and working directory have to be changed to PureBasic_Compilation#.exe and the default compilation folder respectively.

Like I said, I'm not really sure about your requirements, but hope it helps. :)
Texas Instruments TI-99/4A Home Computer: the first home computer with a 16bit processor, crammed into an 8bit architecture. Great hardware - Poor design - Wonderful BASIC engine. And it could talk too! Please visit my YouTube Channel :D
essess
New User
New User
Posts: 9
Joined: Wed Jan 15, 2014 4:07 am

Re: command line arguments behavior

Post by essess »

I'm trying to understand why redirection is not applied when launched from the ide. Hence the reason, that '< test.txt' is interpreted as arguments. This is unexpected behavior for me.

I tried to include the simplest code possible to demonstrate this behavior. All the code does is enumerate the commandline args. I'm not trying to launch anything from my program - my program is showing the arguments it's launched with.

This is the first ide I've used where redirection does not work when launched from the ide. If this is the way it is, fine. If it's not intended behavior (it was certainly unexpected to me) then I'd like to figure out if this is a bug, or a documentation issue. I could not find in the current documentation set if this is 'the way it is'.
User avatar
TI-994A
Addict
Addict
Posts: 2791
Joined: Sat Feb 19, 2011 3:47 am
Location: Singapore
Contact:

Re: command line arguments behavior

Post by TI-994A »

essess wrote:I'm trying to understand why redirection is not applied when launched from the ide.
Hello again esses. If you're trying to set the redirection in Compiler > Compiler Options > Compiler/Run > Executable Commandline, then the answer would be no.

Anyone, please correct me if I'm wrong. :?
Texas Instruments TI-99/4A Home Computer: the first home computer with a 16bit processor, crammed into an 8bit architecture. Great hardware - Poor design - Wonderful BASIC engine. And it could talk too! Please visit my YouTube Channel :D
essess
New User
New User
Posts: 9
Joined: Wed Jan 15, 2014 4:07 am

Re: command line arguments behavior

Post by essess »

Yes! exactly. You phrased it much better than I did. :) I tried to figure out a way around it, but the ide silently inserts the executable name. If it didn't do that, and let me construct my own commandline, then I could do the 'cmd /c' trick if I needed to apply redirection. I could set it up as an external tool, I think, but then I lose the debugger. What's most important to me at this point, is use of the debugger. It's why I'm using the ide.

Did I miss this in the documentation ? I just looked again and didn't see any mention.
How do I file this as a documentation issue (or a bug)?
I suppose the same thing happens under Linux ?

Thanks for sticking with me, I hope to help others someday myself.
User avatar
em_uk
Enthusiast
Enthusiast
Posts: 366
Joined: Sun Aug 08, 2010 3:32 pm
Location: Manchester UK

Re: command line arguments behavior

Post by em_uk »

Hello again. I did already explain why this happens.

Try to look at it this way, the use of < in a command prompt will redirect the contents to the stdin of your command. This redirect is a part of cmd.exe and not the shell

When you use the PB command line option, PB doesn't run the test executable from dos like 'PureBasic_Compilation0.exe < test.txt' but probably uses something like shellexecute/createprocess method to launch the test code where the < doesn't redirect (as it's not the command prompt)

You can test this by compiling your exe, putting it on a drive (for me I saved it to : U:\cmdlind.exe)
Then go to start and and Run and type : U:\cmdline.exe com1 < test.txt and you will see the full output the same as when you run it from in PB.

You can even then create another PB program to call the first :

Code: Select all

RunProgram("U:\cmdline.exe","com1< test.txt","")
And you will see the same output as the IDE.

I don't see any bugs here.
----

R Tape loading error, 0:1
User avatar
em_uk
Enthusiast
Enthusiast
Posts: 366
Joined: Sun Aug 08, 2010 3:32 pm
Location: Manchester UK

Re: command line arguments behavior

Post by em_uk »

If you want to use redirection while having the debugger on, you can do the following :

Compiler Options, Compile/Run, Use Selected Debugger - Standalone GUI Debugger

Tick Create temporary executable in the source directory.

Compile with debugger. Now go to the source folder and find the exe, launch from a command prompt with your redirect arguments.

What it sounds like you want to do is ReadConsoleData and not program parameters :

Code: Select all

ReadConsoleData()

Syntax

Result = ReadConsoleData(*Buffer, Size)
Description

Reads raw input from the console. This function is only supported in non-graphical mode. It can be used to read not line-based data, or text like files redirected to the program through a pipe. 
Parameters

*Buffer The memory buffer to which the data should be read.  
Size The maximum amount of data (in bytes) to be read.  

Return value

Returns the number of bytes actually read from the input. If zero is returned, this means that there is no more input to read. (an end of file was received) 
Remarks

This function waits until there is some input to read. It will only return without reading data if there was an error or an EOF (End Of File) condition. 
Example

  ; This reads a passed image from the console and displays it in a window
  ; Compile this to an exe and run it like "myexe < image.bmp"
  ;
  ; (set "Executable format" To "Console" in the compiler options!)
  ; (works only with Bitmaps and icons unless you use an Image Decoder)
  ;
  OpenConsole()
  TotalSize = 0
  BufferFree = 10000
  *Buffer = AllocateMemory(BufferFree)
  
  Repeat
    ReadSize = ReadConsoleData(*Buffer+TotalSize, BufferFree) ; read a block of data
    TotalSize + ReadSize
    BufferFree - ReadSize
    If BufferFree < 100  ; resize the buffer if it is not large enough
      BufferFree = 10000
      *Buffer = ReAllocateMemory(*Buffer, TotalSize+10000)
    EndIf
  Until ReadSize = 0 ; once 0 is returned, there is nothing else to read
  
  If TotalSize > 0 ; display the image if successful
    If CatchImage(0, *Buffer, TotalSize)
      If OpenWindow(0, 0, 0, ImageWidth(0), ImageHeight(0), "Image", #PB_Window_SystemMenu | #PB_Window_ScreenCentered)
        ImageGadget(0, 0, 0, ImageWidth(0), ImageHeight(0), ImageID(0))
        Repeat
        Until WaitWindowEvent() = #PB_Event_CloseWindow
        End
      EndIf
    EndIf
  EndIf
  MessageRequester("Error", "Not a valid image.")

----

R Tape loading error, 0:1
Post Reply