Is there a way to make the Scala REPL not stop with CTRL-C - scala

I'm using the Scala REPL to interactively test some hash functions I'm building. I'm constantly switching between the product code (Eclipse), the browser and the Scala interpreter, doing copy/paste of values and results. In the mix I'm often doing CTRL-C on the interpreter, exiting the session and loosing all my functions.
Is there any way to let the Scala REPL either ignore CTRL-C or, even better, perform "paste" with it? I'm working on Linux.

I only know how to prevent REPL from exiting. Remapping of CTRL+C to perform copy command could be done in the same way (if there is some command that ables to change keymap w/out restarting terminal -- I don't know is there one). Anyways, to block ^C wrap your REPL invocation in .sh script like this:
#!/bin/bash
#switch off sensitivity to ^C
trap '' 2
# here goes REPL invoke
scala
#get back sensitivity to ^C
trap 2
trap command
defines and activates handlers to be run when the shell receives
signals
or other conditions.
2 is a SIGINT value (that's the signal which is triggered when you press CTRL+C)

The repl already intercepts ctrl-C, but apparently it doesn't work on linux. It does work on osx. If someone who uses linux opens a ticket with sufficient detail to indicate why not, I can fix it.

As an alternative to the native Scala REPL, you can use Ammonite, which does handle Ctrl+C:
# while(true) ()
... hangs ...
^Ctrl-C
Interrupted!
#
The traditional Scala REPL doesn't handle runaway code, and gives you no option but to kill the process, losing all your work.
Ammonite-REPL lets you interrupt the thread, stop the runaway-command and keep going.

Related

Exit from REPL without killing background process

I'm using sys.process inside REPL as kind of shell. There are many uses for scala in a shell. And I invoke some external programs, of course. But I discovered that I could not leave the REPL with a background proccess running. And if I kill the sbt by either Ctrl-C or sending signal, the background process is killed also. I'd like to leave sbt and keep all invoked processes running. How can I do so?
The problem isn't with SBT or Scala but with the child process you created. The child needs to "daemonize" to become independent of the parent process. How to do that depends on what kind of process you are invoking and which OS you are running on. On Linux, using the following script as a wrapper around whatever process you are calling works:
#!/bin/bash
nohup $# 2>&1 >/dev/null &

Why return-to-libc shell using system() exits immediately?

I'm experimenting control-flow hijacking attacks on programs written in C on Linux. I'm trying to perform a simple ret-2-libc attack on a program with the No-eXecutable-stack countermeasure enabled. For this purpose I'm returning to system() function with argument /bin/sh.
But I have a problem: Although my attack works and a shell is spawned successfully, the shell exits immediately after entering the first character! That is, the shell closes after I press any key!
This behavior is also observable in this simple C code:
int main() { system("/bin/sh"); return 0; }
I compile it using: gcc code.c -o system
Why is this? And how can I fix it?
I'm experimenting on Ubuntu-9.04 with kernel 2.6.28 and glibc-2.9-1
Update: The shell becomes interactive if and only if the first key that I press is Enter. That is, if the first character that I enter is a new-line (\n) then the shell remains open and become interactive.
So can anyone explain what's going on here?
Okay I believe that system is successfully calling /bin/sh but it is calling it with the -c flag.
Try:
/bin/bash -c junk
That should behave similarly to what you are seeing. You need to play around with the registers to setup the system call so that /bin/sh is called without the -c flag.

Deal with executing Unix command which produces an endless output

Some unix command such as tail -f or starting a python web server (i.e. cherrypy) will produce an endless output, i.e. the only way to stop it is to Ctrl-C. I'm working on a scala application which execute the command like that, my implemetation is:
import scala.sys.process._
def exe(command: String): Unit = {
command !
}
However, as the command produces an endless output stream, the application hangs there until I either terminate it or kill the process started by the command. I also try to add & at the end of the command in order to run it in background but my application still hangs.
Hence, I'm looking for another way to execute a command without hanging my application.
You can use a custom ProcessLogger to deal with output however you wish as soon as it is available.
val proc =
Process(command).run(ProcessLogger(line => (), err => println("Uh-oh: "+err)))
You may kill a process with the destroy method.
proc.destroy
If you are waiting to get a certain output before killing it, you can create a custom ProcessLogger that can call destroy on its own process once it has what it needs.
You may prefer to use lines (in 2.10; the name is changing to lineStream in 2.11) instead of run to gather standard output, since that will give you a stream that will block when no new output is available. Then you wrap the whole thing in a Future, read lines from the stream until you have what you need, and then kill the process--this simplifies blocking/waiting.
Seq("sh", "-c", "tail -f /var/log/syslog > /dev/null &") !
works for me. I think Randall's answer fails because scala is just executing the commands, and can't interpret shell operators like "&". If the command passed to scala is "sh" and the arguments are a complete shell command, we work around this issue. There also seems to be an issue with how scala parses/separates individual arguments, and using a Seq instead of single String works better for that.
The above is equivalent to the unix command:
sh -c 'tail -f /var/log/syslog > /dev/null &'
If you close the descriptor(s) from which you're reading the process' output, it will get a SIGPIPE and (usually) terminate.
If you just don't want the output, redirect to /dev/null:
command arg arg arg >/dev/null 2>&1
Addendum: This pertains only to Unix-alike systems, not Windows.

Unable to send SIGINT (C-c C-c) to a process running in ansi-term

In Emacs, sometimes I start a shell with ansi-term, and then from this shell I run IPython (another shell) that enters a long loop printing a long, long output.
When this happens, I often want to sendSIGINT to stop the script that IPython is running, but sometimes this takes way too long for IPython to capture Ctrl+C Ctrl+C (there are times when IPython never seems to listen to it). Interestingly, this does not seem to happen when I run it from a regular terminal.
Why is this the case? Is it an Emacs or IPython problem?

How do you run iex from Emacs?

I keep on getting this warning when I run iex using elixir-mode-iex from Emacs:
Warning: could not run smart terminal, falling back to dumb one
I think that this just means that I don't get tab completion, which I'm fine with. But I'd like a smart terminal if it's possible with elixir-mode in Emacs.
elixir-mode-iex uses the comint-mode major mode to interactive with iex. That also means that it's acting just like a dumb terminal (doesn't have the ability to process special escape sequences etc see here).
As a workaround you just could use term which sends any key press directly to the subprocess itself. You could write a function like the following:
(defun my-elixir-iex ()
(interactive)
(term "iex"))
I'm working on an iex Alchemist.el integration, which brings functionality like Inf-Ruby has. But until it's done try to just use iex via term
Cheers
Samuel
It looks like that warning occurs when IEX can't find tty support. You can enable tty mode in emacs by invoking it with -nw.