Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[WIP] REPL shell mode for windows #21294

Closed
wants to merge 4 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 2 additions & 4 deletions base/REPL.jl
Original file line number Diff line number Diff line change
Expand Up @@ -745,11 +745,9 @@ function setup_interface(repl::LineEditREPL; hascolor = repl.hascolor, extra_rep
(repl.envcolors ? Base.input_color : repl.input_color) : "",
keymap_func_data = repl,
complete = ShellCompletionProvider(),
# Transform "foo bar baz" into `foo bar baz` (shell quoting)
# and pass into Base.repl_cmd for processing (handles `ls` and `cd`
# special)
# Pass into Base.repl_cmd for processing (handles `cd` special)
on_done = respond(repl, julia_prompt) do line
Expr(:call, :(Base.repl_cmd), Cmd(Base.shell_split(line)), outstream(repl))
Expr(:call, :(Base.repl_cmd), line, outstream(repl))
end)


Expand Down
37 changes: 29 additions & 8 deletions base/client.jl
Original file line number Diff line number Diff line change
Expand Up @@ -82,17 +82,22 @@ answer_color() = text_colors[repl_color("JULIA_ANSWER_COLOR", default_color_answ
stackframe_lineinfo_color() = repl_color("JULIA_STACKFRAME_LINEINFO_COLOR", :bold)
stackframe_function_color() = repl_color("JULIA_STACKFRAME_FUNCTION_COLOR", :bold)

function repl_cmd(cmd, out)
shell = shell_split(get(ENV,"JULIA_SHELL",get(ENV,"SHELL","/bin/sh")))
shell_name = Base.basename(shell[1])
function repl_cmd(line::AbstractString, out)
if is_windows()
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should use @static when conditioning on the OS inside a function

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

not unless you're emitting code that doesn't compile on multiple platforms, or you really need to eliminate the comparison for runtime performance. better to leave the static out if neither is the case, have all branches at least get compiled.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think on v0.6, code is conditionally compiled with and without @static
So maybe there's no runtime performance difference?

Both test1() and test2() produce the same llvm:

test1() = is_windows() ? 1 : "a"
test2() = @static is_windows() ? 1 : "a"
julia> @code_llvm test1()

; Function Attrs: uwtable
define i64 @julia_test1_68517() #0 !dbg !5 {
top:
  ret i64 1
}

julia> @code_llvm test2()

; Function Attrs: uwtable
define i64 @julia_test2_68518() #0 !dbg !5 {
top:
  ret i64 1
}

shell = shell_split(get(ENV, "JULIA_SHELL", "cmd"))
shell_name = isempty(shell) ? "" : lowercase(splitext(basename(shell[1]))[1])
else
shell = shell_split(get(ENV, "JULIA_SHELL", get(ENV,"SHELL","/bin/sh")))
shell_name = basename(shell[1])
end

cmd = Cmd(shell_split(line))

if isempty(cmd.exec)
throw(ArgumentError("no cmd to execute"))
elseif cmd.exec[1] == "cd"
elseif cmd.exec[1] == "cd" && length(cmd.exec) <= 2
new_oldpwd = pwd()
if length(cmd.exec) > 2
throw(ArgumentError("cd method only takes one argument"))
elseif length(cmd.exec) == 2
if length(cmd.exec) == 2
dir = cmd.exec[2]
if dir == "-"
if !haskey(ENV, "OLDPWD")
Expand All @@ -108,7 +113,23 @@ function repl_cmd(cmd, out)
ENV["OLDPWD"] = new_oldpwd
println(out, pwd())
else
run(ignorestatus(@static is_windows() ? cmd : (isa(STDIN, TTY) ? `$shell -i -c "$(shell_wrap_true(shell_name, cmd))"` : `$shell -c "$(shell_wrap_true(shell_name, cmd))"`)))
if is_windows()
interpolated_line = eval(parse(string('"', escape_string(line), '"')))
if shell_name == ""
command = cmd
elseif shell_name == "cmd"
command = Cmd(`$shell /s /c $(string('"',interpolated_line,'"'))`, windows_verbatim=true)
elseif shell_name == "powershell"
command = `$shell -Command $interpolated_line`
elseif shell_name == "busybox"
command = `$shell sh -c $interpolated_line`
else
command = `$shell $interpolated_line`
end
run(ignorestatus(command))
else
run(ignorestatus(isa(STDIN, TTY) ? `$shell -i -c "$(shell_wrap_true(shell_name, cmd))"` : `$shell -c "$(shell_wrap_true(shell_name, cmd))"`))
end
end
nothing
end
Expand Down
2 changes: 1 addition & 1 deletion base/precompile.jl
Original file line number Diff line number Diff line change
Expand Up @@ -331,7 +331,7 @@ precompile(Base.rehash!, (Dict{Any,Any}, Int))
precompile(Base.rehash!, (Dict{UInt8, Any}, Int))
precompile(Base.reinit_stdio, ())
precompile(Base.repeat, (String, Int))
precompile(Base.repl_cmd, (Cmd, Base.Terminals.TTYTerminal))
precompile(Base.repl_cmd, (String, Base.Terminals.TTYTerminal))
precompile(Base.require, (Symbol,))
precompile(Base.Distributed.remoteref_id, (Base.Distributed.RemoteChannel,))
precompile(Base.rsearch, (String, Char))
Expand Down