"C:>echo 123 | set /p xyz=" at a cmd prompt doesn't set/change "xyz".
Is there another way to set a variable from piped standard input (without temp files etc)? Question is related to http://www.robvanderwoude.com/variableexpansionbug.html, and could have interesting uses inside a "for" with enabledelayedexpansion, for example
-------- @echo off echo. setlocal enabledelayedexpansion for %%x in ("%%^^&^!") do ( echo "%%~x" (echo "%%~x") | more ) --------
gives
-------- "%&" "%^&!" --------
where the second line could be useful if "captured" into a variable.
On Jul 12, 6:12 am, "Liviu" <lab...@gmail.c0m> wrote:
> <001.dmi...@gmail.com> wrote > On 12 ÉÀÌ, 05:48, "Liviu" <lab...@gmail.c0m> wrote: > >> "C:>echo 123 | set /p xyz=" at a cmd prompt doesn't set/change "xyz".
> >> Is there another way to set a variable from piped standard input > >> (without temp files etc)?
> > No. Only temp files and `for /f`
> I'd take 'for /f ' if only it worked ;-)
It does work. But not the way you used it :) Try this:
----setfromstdin.bat @echo off setlocal for /f "delims=" %%x in ('more') do set xyz=%%x set xyz ----EOF
C:\> echo 123| setfromstdin.bat xyz=123
To understand what happens you have to know how anonymous pipes are handled in NT. Both ends of the pipe are launched in separate child processes. Once all the commands are executed, those processes are terminated and their environments destroyed, so any environment changes will not survive (unless you use some utility capable of setting the environment of the parent process).
Now, on to the supposed bug with delayed expansion that you link to in your original post. There is no bug, it's the expected behaviour. Let's look at the example from the link http://www.robvanderwoude.com/variableexpansionbug.html :
----BOF @echo off setlocal enabledelayedexpansion set myvar=value ( echo.!myvar! ) | more endlocal ----EOF
The reason it doesn't work is because 'echo.!myvar!' is execuded in a separate 'cmd.exe' and by default delayed expansion is disabled in command interpreter. So let's enable it and see what happens:
<t.m.trzec...@gmail.com> wrote On Jul 12, 6:12 am, "Liviu" <lab...@gmail.c0m> wrote:
> <001.dmi...@gmail.com> wrote >> On 12 ÉÀÌ, 05:48, "Liviu" <lab...@gmail.c0m> wrote: >> >> "C:>echo 123 | set /p xyz=" at a cmd prompt doesn't set/change >> >> "xyz".
>> >> Is there another way to set a variable from piped standard input >> >> (without temp files etc)?
>> > No. Only temp files and `for /f`
>> I'd take 'for /f ' if only it worked ;-)
> It does work. But not the way you used it :) Try this:
Thanks, but it still does not work the way I asked ;-)
> ----setfromstdin.bat > @echo off > setlocal > for /f "delims=" %%x in ('more') do set xyz=%%x > set xyz > ----EOF
> C:\> echo 123| setfromstdin.bat > xyz=123
The .bat is not setting the environment in the caller process. In fact it's not too different from the example I gave with the one-line for /f at the cmd prompt, where you could see the set xyz=123 being executed, but then "xyz" was still undefined once control returned to the prompt. Using your batch does pretty much the same...
---- C:>echo 123 | setfromstdin.bat xyz=123
C:>set xyz Environment variable xyz not defined ----
> To understand what happens you have to know how anonymous pipes > are handled in NT. Both ends of the pipe are launched in separate > child processes. Once all the commands are executed, those processes > are terminated and their environments destroyed, so any environment > changes will not survive (unless you use some utility capable of > setting the environment of the parent process).
Would you know of such utility usable in batch files?
That said, I believe your explanation is close to what's going on internally. However, it is not an intrinsic limitation of anonymous pipes. If anything, it's a careless (mis)use of them by cmd.
> Now, on to the supposed bug with delayed expansion that you link to > in your original post. There is no bug, it's the expected behaviour. > [...] > The reason it doesn't work is because 'echo.!myvar!' is execuded in a > separate 'cmd.exe' and by default delayed expansion is disabled in > command interpreter. So let's enable it and see what happens [...]
Yes and no. Yes, I see your point. No, because you could make literally the same point if 'echo.!myvar!' was not enclosed in parantheses, yet it works as expected in that case.
On Sat, 12 Jul 2008 11:15:35 -0500, "Liviu" <lab...@gmail.c0m> wrote: >> are terminated and their environments destroyed, so any environment >> changes will not survive (unless you use some utility capable of >> setting the environment of the parent process).
>Would you know of such utility usable in batch files?
>>> are terminated and their environments destroyed, so any environment >>> changes will not survive (unless you use some utility capable of >>> setting the environment of the parent process).
>>Would you know of such utility usable in batch files?
> What do you want to do, in specific terms?
Fight the "!" demons ;-) Quoting from the top post: [...] could have interesting uses inside a "for" with enabledelayedexpansion, for example
-------- @echo off echo. setlocal enabledelayedexpansion for %%x in ("%%^^&^!") do ( echo "%%~x" (echo "%%~x") | more ) --------
gives
-------- "%&" "%^&!" --------
where the second line could be useful if "captured" into a variable.
> Nothing to do with malware is it? ;-)
Not at all, unless you classify enabledelayedexpansion as malware ;-)
> >>> are terminated and their environments destroyed, so any environment > >>> changes will not survive (unless you use some utility capable of > >>> setting the environment of the parent process).
> >>Would you know of such utility usable in batch files?
> > What do you want to do, in specific terms?
> Fight the "!" demons ;-) Quoting from the top post: š[...] could have > interesting uses inside a "for" with enabledelayedexpansion, for example
> -------- > @echo off > echo. > setlocal enabledelayedexpansion > for %%x in ("%%^^&^!") do ( > š echo "%%~x" > š (echo "%%~x") | more > ) > --------
> gives
> -------- > "%&" > "%^&!" > --------
> where the second line could be useful if "captured" into a variable.
> > Nothing to do with malware is it? ;-)
> Not at all, unless you classify enabledelayedexpansion as malware ;-)
@echo off
for %%x in (%%^&!) do set "var=%%x" && call:1 goto:eof
On Jul 12, 5:15 pm, "Liviu" <lab...@gmail.c0m> wrote:
> <t.m.trzec...@gmail.com> wrote > > It does work. But not the way you used it :) Try this:
> Thanks, but it still does not work the way I asked ;-) > The .bat is not setting the environment in the caller process. In fact > it's not too different from the example I gave with the one-line for /f > at the cmd prompt, where you could see the set xyz=123 being executed, > but then "xyz" was still undefined once control returned to the prompt. > Using your batch does pretty much the same...
Yes, that's correct. What I wanted to show was that you can read from stdin in your parrent batch and set the evironment accordingly. If that doesn't work for you then you are left with temp files or some 3rd party utilities.
> > changes will not survive (unless you use some utility capable of > > setting the environment of the parent process).
> Would you know of such utility usable in batch files?
I think it was 'setenv' but I'm not sure. Just search this group and you will surely find it.
> That said, I believe your explanation is close to what's going on > internally. However, it is not an intrinsic limitation of anonymous > pipes. If anything, it's a careless (mis)use of them by cmd.
It's actually easy to test if this explanation is true. Run C:\>echo|(echo&ping 1.1.1.1) and check windows task manager. You will briefly see an extra cmd.exe process while piped commands are executed. So my explanation wasn't 100% accurate. Only receiving end of the pipe is launched in a separate process.
If that's a 'careless (mis)use' I don't know but that's how things work on NT. What can you do about it?
> > Now, on to the supposed bug with delayed expansion that you link to > > in your original post. There is no bug, it's the expected behaviour. > > [...] > > The reason it doesn't work is because 'echo.!myvar!' is execuded in a > > separate 'cmd.exe' and by default delayed expansion is disabled in > > command interpreter. So let's enable it and see what happens [...]
> Yes and no. Yes, I see your point. No, because you could make literally > the same point if 'echo.!myvar!' was not enclosed in parantheses, yet it > works as expected in that case.
Yes, you are right. I've jumped too far with my conclusions. It is a bug, indeed. Interestingly enough, if you enable delayed expansion globally in windows' registry then the following works (even without restarting of command interpreter!)
>> Thanks, but it still does not work the way I asked ;-) >> The .bat is not setting the environment in the caller process. In >> fact it's not too different from the example I gave with the one- >> line for /f at the cmd prompt, where you could see the set xyz=123 >> being executed, but then "xyz" was still undefined once control >> returned to the prompt. Using your batch does pretty much the same...
> Yes, that's correct. What I wanted to show was that you can read from > stdin in your parrent batch and set the evironment accordingly. If > that doesn't work for you then you are left with temp files or some > 3rd party utilities.
What is wrong with using temp files? As long as a batch is written to remove them, there should be no reason to avoid them. Sure you have to write one or two extra lines of code but it's not that big a deal.
-- Todd Vargo (Post questions to group only. Remove "z" to email personal messages)
On Sat, 12 Jul 2008 11:55:10 -0500, "Liviu" <lab...@gmail.c0m> wrote: >"foxidrive" <got...@woohoo.invalid> wrote in message >news:ognh74lb3ohsotsjsck04lve2abqnhmgt8@4ax.com... >> On Sat, 12 Jul 2008 11:15:35 -0500, "Liviu" <lab...@gmail.c0m> wrote:
>>>> are terminated and their environments destroyed, so any environment >>>> changes will not survive (unless you use some utility capable of >>>> setting the environment of the parent process).
>>>Would you know of such utility usable in batch files?
>> What do you want to do, in specific terms? >Fight the "!" demons ;-) Quoting from the top post:
Please explain specifically what you need to do and under what circumstances.