Nasty gotcha: Powershell aliases that match commands you might want to run

PowerShell has a bunch of aliases, but some of them collide with programs you might want to run.

PowerShell Get-Alias

will print all the aliases. These two conflict with programs that come with Windows:

  • sc: Set-Content vs. sc.exe (service control)
  • fc: Format-Custom vs. fc.exe (file compare)

I've seen email threads where somebody says, for example,

Try running these commands:

sc stop someservice
sc start someservice

and the other person says, "It doesn't work." When I run the second command, it says that it cannot reconfigure the service because it is already running."

Eventually, we figure out that the reason is that the other person uses PowerShell as their default command shell, and the command happens to collide with a PowerShell alias. What's particularly devious is that Set-Content command is happy to accept start someservice as its command line. It creates a text file called start with the contents someService.

Comments (34)
  1. warrens says:

    At a Powershell prompt, hit tab twice after typing “sc” or “fc” (or “wget” if you have it installed) to have “.exe” appended, which will get around this problem.

  2. florian says:

    Fortunately, this does not apply to batch files run from a PowerShell prompt – I’d have to do a lot of work, otherwise!

    1. Darran Rowe says:

      Since powershell doesn’t understand batch files, it spins up cmd.exe to do the processing.

  3. Antonio Rodríguez says:

    That’s the problem with replacing the default command shell, which I think was a really bad idea, knowing how many tech notes, tips and workarounds rely on cmd.exe. All the arguments against an “expert mode” in Windows apply also to the replacement of CMD.exe with a semi-compatible alternative shell (be it PowerShell or bash).

    On the other hand, if you provide PowerShell and leave CMD.exe as the default shell, the power users, who know what they are doing, will set as default, and regular users will keep CMD.exe. Right, some PM would go without a bonus because the usage of PowerShell didn’t grow much, but users would be happier.

    1. Fred says:

      This kind of logic doesn’t make any sense. You don’t want to perpetuate the use of CMD, you want new users to start from PowerShell right away. They don’t have any knowledge either way, so they’re the ones you need to guide down the right path, whereas legacy users who have used CMD their whole lives will instantly notice they have the wrong terminal open. “This isn’t the right program, it’s all blue!”

      1. BZ says:

        And MS has never changed the color scheme on existing programs before? (this isn’t Minesweeper, it’s all blue)

      2. Antonio Rodríguez says:

        Yes, its like all users, even my Internet auntie, will see the blue background and say “I must adapt this 15-year-old tutorial to this new command interpreter”. That’s really sound logic!

  4. Fred says:

    423 days ago: Curl author asks Microsoft to remove ‘curl’ and ‘wget’ aliases from PowerShell

    1. voo says:

      That’s a weird point anyhow: The ls alias certainly doesn’t behave exactly like the Linux equivalent either, it’s just offering an easy way for people coming from *nix to find the native Windows equivalents.

      There are millions of scripts out there relying on the functionality and anybody who installs curl/wget on Windows should be capable enough to remove those aliases if he or she doesn’t want to use them. Or just write wget.exe or curl.exe.

      Seems mostly much ado about nothing..

      1. cheong00 says:

        Don’t try to assume the command as something when it’s not, as least not try to assume well known ones.

        Imagine the frustration if there is PS alias for “net” or “makecert” command that does other things.

      2. Karellen says:

        Sorry, how does the presence of the “ls” alias help people coming from *nix to find the native Windows equivalent (“dir” or “Get-ChildItem”)?

        Surely it puts up a barrier to finding the native equivalent, because why would you bother to look for the native equivalent when “ls” works (for suitable values of “works”)?

        1. Joshua says:

          powershell’s ls doesn’t work either. Why bother?

        2. voo says:

          Because typing “ls” in PowerShell just works and typing man ls will give you the help for the actual Get-ChildItem command if you’re then later (!) interested in finding out more.

          Someone opening PowerShell for the first time will easily be able to navigate around in the filesystem if they know either Batch or Bash – and that without having to read a book. Which is a giant plus and one of the main reasons PowerShell uptake was so strong from the beginning.

          Yes yes I know, everybody should just read 300 pages of documentation before ever trying to get work done, yada yada. In the real world *nobody* does that and if your tool that has to overcome 30+ years of habit requires people to actually read documentation it will be just dead and in the water.

          And as already established, the people who prefer to not see any aliases can just look up the documentation for PowerShell providers and the alias provider in particular and remove all of them.. it’s a 5 seconds affair.

          This all obviously only applies to PowerShell on Windows – but then so do the aliases for common Linux commands, they don’t exist in PowerShell core on Linux.

    2. Antonio Rodríguez says:

      The other way around would have been better. 4DOS supported alias 30 years ago – and they were very useful. But they didn’t define any aliases by default. Instead, they listed a dozen or so useful ones in the help file, so the user could install them if s/he wanted.

      At those times, with disk access times measured in hundreds of miliseconds (remember those 20 MB MFM full-height hard drives?) and little to no disk cache, aliases made a big speed difference. But nowadays, disk subsystems (SATA/SAS, SSD, RAID, huge caches…) are so fast that there is almost no difference between built-in aliases and “redirection” scripts. I don’t think that aliases are an essential feature anymore.

      In fact, 4DOS and 4NT went the way CMD should have gone: adding new useful features (procedures, expressions, built-in function and operators, more internal commands…) while maintaining full backwards compatibility.

      1. Someone says:

        Where is the connection between “aliases” in a command shell (which merely safes you some typing) and harddisk speed?

        1. Beldantazar says:

          It makes a difference because with a redirection script that say made “rmall” call “rm -rf *” or whatever, the harddrive would have to load the script and then the script would invoke rm, that’s two disk accesses minimum not counting and disk used by the actual command. With an alias, the shell would directly call “rm -rf *” when you typed in “rmall” which meant that you only did a single disk access instead, potentially huge savings of time on the days of very slow storage.

    3. Wear says:

      That is a fascinating thread. Reminds me of reading Wikipedia talk pages. Everyone is very committed to their specific point of view.

      1. yukkuri says:

        That sure is a polite way to put it :)

    1. Karellen says:

      Doh. Beaten by Fred. Shouldn’t have taken so long reading the comments on the pull request before finally clicking “post comment” on my response here…

  5. 640k says:

    Nasty gotcha: cmd.exe had alias that you might want to run. It’s called progress.

  6. morlamweb says:

    A another for the entry: “Because everybody has CMD as their default command shell, right?” I’ve avoided countless hassles by typing the file extension by habit, especially when people usually copy/paste from email.

  7. Joshua Schaeffer says:

    Instead of dealing with all this, how hard would it be to just rewrite CMD.EXE so we’re never in danger of losing control of it? I’m the powerest of power users and I can’t stand PowerShell. It’s slower than snail crap and obfuscates the stuff we’ve already been doing. They didn’t realize that text output speed will literally affect execution speed when you’re blocking on $conout. Or maybe the WPF team didn’t realize that. Someone failed on a deep technical level and it’s embarrassing. They also should have based it on the shell namespace not the filesystem. Not all consumer storage devices have beautiful filesystem mount points for batch operations.

  8. I believe PowerShell has Start-Service, Set-Service and Stop-Service commands of its own.

    1. Neil says:

      That’s not very useful if you think the user’s running Command Prompt.

      1. 640k says:

        If you assume a specific shell, make sure you run it.

        1. morlamweb says:

          Better yet, state the expected command shell before spewing out the command lines. It’s not much work to write “Try running these commands in CMD.exe:”.

  9. Karellen says:

    I wonder, does powershell have an equivalent to the bourne shell[0] (and derivatives, incl. bash[1]) builtin “type”, which prints the type of command that a word is? e.g. if it’s a function, alias, file, keyword, etc…


  10. Martin Ba. _ says:

    Another example where the PS people seem to live in a world totally disconnected from the rest of the system.
    Windows had sc.exe for ages, and it is *not* an esoteric command: Adding an alias that’s named the same just shows how little regard the PS crew has for interoperating with anyone else. (And yes, this is just a small puzzle piece, otherwise I’d not have bothered.)

    1. voo says:

      And PowerShell also provides built-in utils that are VASTLY superior to sc.exe while still allowing you to call the external utility by writing.. sc.exe.

      But then if you’re using sc.exe instead of the PowerShell tools to work with services, why not just stick with cmd to begin with?

  11. florian says:

    I must have been living under a rock, and haven’t even noticed that PowerShell is now open source… but somehow, I’d be much more excited to browse the original CMD.EXE code base…

    1. Erkin Alp Güney says:

      When Windows source code is published.

  12. Gee Law says:

    Idiomatically you can use `Start-Process` to start native utilities, which I have always advocated. This solves the problem that in *nix you usually have no extension for executable binaries and that you cannot use `.\xyz` to invoke `xyz` from `PATH`.

Comments are closed.

Skip to main content