bizarre behavior of system() in Ruby - ruby

I have set up shuffle_play.rb in Ruby by Example to work on Windows, with mpg123 instead of ogg123. The critical part is a method called play_file, which initially I wrote like this
def play_file(file)
system("mpg123 \"#{file}\"")
end
I have mpg123 in the same directory as my script ... it didn't work. But this does work:
def play_file(file)
system("mpg123.exe \"#{file}\"")
end
I reckon it's because I don't have working directory in %PATH% (and indeed the problem goes away when I add it) but even then I don't know enough about Windows to know the difference. Could someone explain the rationale for this?

Probably the examples assume that you're on a *nix variant such as Linux or Mac. In those Operating Systems, the program is called mpg123, because those OS, don't care about extensions, the just check that the file has an executable attribute
On windows things are very different. Windows decides if something is a program depending on the extension (.exe, .com, .bat, .cmd, etc.). So the program in windows has to be called mpg123.exe. If you open a command line on windows, you can run the program without specifying the extension, as windows automatically tries the different extensions. This behaviour of trying different extensions happens ONLY in the command line and not when you try to invoke a program from another one.
There a environment variable called PATHEXT that list in which order windows tries the different extensions. On my computer that list is:
C:\Windows\System32>echo %PATHEXT%
.COM;.EXE;.BAT;.CMD;.VBS;.VBE;.JS;.JSE;.WSF;.WSH;.MSC;.RB;.RBW
I hope it was clear. And a suggestion if you want to code in ruby, install Linux or get a Mac.

Related

Is running a Windows .EXE inherently slower via Cygwin than via BAT?

We are running a Windows .EXE file via a Cygwin script and are encountering performance issues. I have seen various posts about Cygwin performance issues, including this one, one of whose answers delves enough into Cygwin internals to make me think there could be a problem. However, these posts do seem to be more about startup time, tab completion, etc. Before we launch on a benchmarking witch hunt, I was hoping to ask: is there any intrinsic reason why a Windows .EXE could run slower if kicked off from Cygwin vs. BAT?
Not the actual program, no.
Housekeeping and stuff before running the program may vary. Cmd probably calls CreateProcess directly. Cygwin's bash may first do argument parsing, wildcard expansion, fork via Cygwin's slow implementation and call exec with the parsed arguments, which Cygwin has to piece together into a string again to pass to CreateProcess. But in the end, a new process is created which has no ties to its parent anymore. So how fast your program runs entirely depends on that program, not on who launched it.

Where to put batch file in Windows so that it is always accessible, without changing the PATH?

I have a NSIS installer for a program and change PATH settings to make the program always accessible from the command-line. Manipulating the PATH has however some adverse effect, such as other programs picking up DLLs from that directory.
In order ot avoid fiddling with PATH, I would like to create a wrapper .bat file calling the executable. Where should I put this .bat file so that it is always found? Is c:\Windows\System32 (more precisely, $SYSDIR in NSIS) appropriate in terms of good practices?
I am targetting 64bit systems, XP and Seven.
I'm personally not a big fan of apps that do anything with my %path%, people that work with command line tools probably know how to change %path% or use doskey (alias).
If you want to use a batch file you should be able to get away with a one-liner like #"c:\path\to\my\app.exe" %* but a batch file wrapper like this makes the Ctrl+C handling very annoying.
Putting it in $windir should make it work with both x86 and x64 shells without having to worry about filesystem redirection...

Writing script that runs on Windows and Mac

I need to write a small script that renames some files in a directory. This script needs to be run on Mac and Windows.
What is the best scripting language for this? I want to write something that runs just by calling it and there is no need to install anything else.
For example, writing a Perl script and compiling it to run on Windows and then compiling it to run on Mac. Can I do this?
Any other, more elegant solution?
Nothing matches your criteria. You will need to install something (e.g. perl) if you want something that runs on both systems.
If you had perl on both systems, you could indeed write a program that runs on both. You wouldn't even need two binaries as you suggest since Perl programs are distributed as source. (perl compiles them when it loads them, and even then, they are compiled to the same form on all systems.)

How to make a Python PyQT program not open the command line in Windows

I have a Python program that is mostly complete, and there is one thing that I'd like to change, which may or may not be possible.
This program uses PyQT to display a GUI and I have it pretty much pinned up so I was wondering if I can make Python not open up a termianl when I open the program.
I am using Windows XP right now, but the machines it will run on will be Windows 7. I generally work with Linux, so I'm not terribly familiar with Windows.
If the terminal has to be there, it's no big deal, but I feel like it's extraneous at this point.
Thanks!
Use the python extension .pyw.
E.g program.pyw
This causes your program to be run with pythonw.exe instead of python.exe which suppresses the terminal.

alternative bash for windows / or help on cygwin with specific tasks

my goal: to create a suite of scripts that do some common system tasks, which include these
copy/move/list/search/grep files
watch/start/stop processes
run queries against Oracle via sqlplus
i grew accustomed to using Cygwin/bash to ease my life at work, and frankly speaking, i don't want to move away from bash language and start learning PowerShell, for example - so i started searching for a way to run bash scripts on Windows, ... preferably something alternative to Cygwin.
the truth is that i am still not pleased with Cygwin installation, and the fact that there is no simple way around it, that it is targeting more or less expert users, and there are a number of things that might pop up during the installation. i mean. what i am trying to do now is to write a suite of scripts that will target someone less expert than me (and i am in no way a real expert) - in most cases some kind of an administrator who doesn't want to know the script details.
i am thinking that this user will also want to be able to run these scripts on another machine, and i want to be able to explain him/her how to do it, without just saying, call the support, and, me, eventually (so that we can install cygwin on another machine etc etc.)
i tried MinGW(msys) but it also needs manual steps to set things up - i mean, these manual steps have become something of a de facto standard in these Windows ports (sorry, maybe i have a mood for bragging). win-bash looked like it could be a solution, but i ended up trashing it too, because of the old bash version, and its inability to do things i was able to do in cygwin - specifically
here documents
things like "cmd /C dir *" (don't know why) - and yes, i do cmd /C dir in cases i am in some kind of shared network folder with thousands of files, and ls is significantly slower than dir
my questions at last:
am i doomed to use PowerShell? i guess i will, reluctantly, if i have to
is there a simple pre-packaged "slim" cygwin installation.. or, portable cygwin, even better? there is a cygwin-portable project on sourceforge, but it's not that doesn't need those manual steps, again, apparently - is there a way to automate those steps, perhaps? and if there is, i wonder why somebody hasn't done it already? - and then, would it be possible to call bash scripts from Windows command prompt using a simple command like "bash somescript.sh"?
thanks for your attention.
As mentioned here, the Cygwin installation can totally be scripted and parametrized to ran in a silently and automatic mode.
If you define the minimal list of cygwin packages you need, just use a little .bat script that call the cygmin setup executable like this
setup.exe --packages=list_of_packages_you_need --quiet-mode
If you wrap the cygwin install process, it should be tolerable for a less technical user.
The cygwin install can be streamlined using command-line args;
http://sources.redhat.com/ml/cygwin-apps/2003-03/msg00526.html
You can also automate the install of most cygwin packages through cyg-apt.
I haven't verified this but I suspect that msys implements a *nix look alike by creating windows executable versions of system commands. All of the common commands have an executable on my install of msys. If that is true then it should be possible to use them separate from a complete install.
Try copying "bash.exe", "cp.exe", etc. from the msys bin directory to a machine/vm that does not have an msys install and see if it works. You may need to copy some dll's or shared libraries as well. A windows dependency checker program would show which dll's an executable is using.
You could package up the stuff you use and make a simple installer or just copy the files with your scripts.
Take a look at MKS Toolkit. Unlike Cygwin, it can live within the Windows world. Files end in CR/LF like Windows files, and you don't have that /cygdrive/c stuff. Naked drive letters work fine in MKS Toolkit.
A few caveats:
I haven't used MKS Toolkit in a long time. See following reason.
MKS Toolkit is (sit down for this) $600 per license. Ouch! That's why I use Cygwin even though I don't think it's as good or works as well.
It's Kornshell based and not Bash (although this may be a bit different). Kornshell and BASH are 95% alike. However, that last 5% gets you. I actually like Kornshell better than BASH in many respects. Kornshell has the print statement which is way superior than the echo statement. Variable names don't disappear in blocks. You can easily do double loops because almost all the commands can take unit numbers of input and output. However, Kornshell doesn't have those neat escape characters in the prompt, and it's hard to find the exit status of a command in the middle of the pipeline.

Resources