emacs: Automatically open corresponding file in another instance - c++

I want something similar to Emacs C++, opening corresponding header file except that I want to
1) Always automatically open the corresponding header; and
2) Do that in another emacs instance (if someone came up with a solution that made all other emacs instances do this, it would be fine also.)
Note that I use emacs in the terminal mode so I can't do https://superuser.com/questions/102163/how-to-split-emacs-over-a-dual-monitor (or at least I do not know how).

A simple solution to 2) is to run an emacs instance with
server-mode enabled in the second terminal and command it from the
main emacs instance by using server-eval-at.
To launch the slave, run:
$ emacs --eval '(progn (setq server-name "ff-slave") (server-mode 1))'
Then use the following code to command it:
(require 'server)
(require 'find-file)
(defun command-ff-slave ()
(interactive)
(save-excursion
(let ((b (ff-other-file-name)))
(if (null b)
(message "Found no other file")
(server-eval-at "ff-slave"
`(find-file ,b))))))
Calling command-ff-slave from the main emacs instance
should open any related file in a new buffer on the slave server.

Related

How to run an interactive CLI program from within Clojure?

I'd like to run an interactive CLI program from within Clojure (e.g., vim) and be able to interact with it.
In bash and other programming languages, I can do that with
vim > `tty`
I tried to do the same in Clojure:
(require '[clojure.java.shell :as shell])
(shell/sh "vim > `tty`")
but it just opens vim without giving me tty.
Background: I'm developing a Clojure CLI tool which parses emails and lets a user edit the parsed data before saving them on the disk. It works the following way:
Read a file with email content and parse it. Each email is stored as a separate file.
Show a user the parsed data and let the user edit the data in vim. Internally I create a temporary file with the parsed data, but I don't mind doing it another way if that would solve my issue.
After a user finished editing the parsed data (they might decide to keep it as it is) append the data to a file on a disk. So all parsed data are saved to the same file.
Go to 1st step if there are any files with emails left.
This code relies on Clojure Java interop to make use of Java's ProcessBuilder class.
(defn -main
[]
;use doseq instead of for because for is lazily evaluated
(doseq [i [1 2 3]]
;extract current directory from system variable
(let [file-name (str "test" i ".txt")
working-directory (trim-newline (:out (sh "printenv" "PWD")))]
(spit file-name "")
;this is where fun begins. We use ProcessBuilder to forward commands to terminal
;we pass a list of commands and their arguments to its constructor
(let [process-builder (java.lang.ProcessBuilder. (list "vim" (str working-directory "/" file-name)))
;inherit is a configuration constant
inherit (java.lang.ProcessBuilder$Redirect/INHERIT)]
;we configure input, output and error redirection
(.redirectOutput process-builder inherit)
(.redirectError process-builder inherit)
(.redirectInput process-builder inherit)
;waitFor used to block execution until vim is closed
(.waitFor (.start process-builder))
)
;additional processing here
)
)
;not necessary but script tends to hang for around 30 seconds at end of its execution
;so this command is used to terminate it instantly
(System/exit 0)
)

Troubleshooting Emacs Tramp Connection that Used To Work--Password or Shell Regexp Wrong?

I'm trying to troubleshoot why an emacs+tramp connection that used to work doesn't now. At first I thought it might be an Aquamacs problem, but I loaded Emacs.app on OSX, based on version 23.3 (9.0), and it doesn't work either. The remote host runs FreeBSD 7.4 and the user shell defaults to /usr/local/bin/bash.
If I try to open a file such as:
Find file: /username#remote_host:~/folder/
...the cursor in the minibuffer stops at:
Find file: /username#remote_host
...and I can't type anything further. Confounding this, I can't C-g to stop it, either. Emacs just locks up. It times out after a minute or so, but until then is unusable.
The relevant lines of my .emacs file are:
(require 'tramp)
(setq tramp-debug-buffer t)
(setq tramp-verbose 9)
(setq tramp-default-method "ssh")
(setq tramp-password-prompt-regexp ".*[Pp]assword: *$")
(setq tramp-shell-prompt-pattern "^[^;$#>]*[;$#>] *")
(setq password-cache-expiry nil)
And the password and shell prompts on the machine in question (anonymized) look like:
Password:
[username#remote_host ~]$ # with a single space at the end
The value of tramp-password-prompt-regexp is ".*[Pp]assword: *$"
The value of tramp-shell-prompt-pattern is "^[^;$#>]*[;$#>] *"
And lastly, the last few lines of the debug buffer:
14:36:40.271851 tramp-get-connection-property (7) # check-remote-echo nil
14:36:41.090876 tramp-wait-for-regexp (6) #
are you awake
#$
14:36:41.091037 tramp-wait-for-regexp (1) # File error: [[Regexp `\(^\|\)[^#$
?$' not found in 60 secs]]
I'm not sure where the different version of the shell regexp are coming from, but in any case, I'm never even getting to the password prompt.
Any ideas what I might be doing wrong?
Addendum
Using GNU Emacs 22.1.1 (mac-apple-darwin, Carbon Version 1.6.0), Tramp version 2.0.55, works. I'm reluctant to rely on that, however, as it is based on the terminal window and I've shuffled Cmd, Ctrl, and Caps Lock around to make my workstation feel more like my home machine, then told Emacs to treat the Cmd key as an alternate Ctrl; unfortunately, the terminal window traps several Cmd-key combinations.
Furthermore
Downloaded the Emacs-22.3-i386-10.5.7.dmg from Emacs For OS X, which uses tramp 2.0.58-pre. That works too, and has fewer issues with the environment trapping key combinations. But I still don't understand why the Aquamacs and later Carbon Emacs versions quit working.

How to load cedet, semantic et. al only when .cxx,.h .cpp files are open

Because I use Emacs for many things these days I would like to only load cedet.el when I open a c/C++ source or header and not everytime emacs starts since it takes a significant toll on the startup time.
Right now the beginning of my init file looks like this:
(load-file "~/.emacs.d/plugins/cedet/common/cedet.el")
(semantic-load-enable-excessive-code-helpers)
;;(semantic-load-enable-semantic-debugging-helpers)
(setq senator-minor-mode-name "SN")
(setq semantic-imenu-auto-rebuild-directory-indexes nil)
(global-srecode-minor-mode 1)
(global-semantic-mru-bookmark-mode 1)
And it keeps going.
Is there a way to do this?
my emacs startup improved dramatically after i learned to use eval-after-load and autoload.
if you have a mode you only want loaded when you open a file of the type, add something like this to your .emacs (assuming foo-mode is defined in foo-mode.el on your load path):
(autoload 'foo-mode "foo-mode" nil t)
(add-to-list 'auto-mode-alist '("\\.foo\\'" . foo-mode))
if you have some helper libraries which you only want loaded after you load a "main" library, add something like this to your .emacs (assuming bar-mode is a secondary mode which enhances foo-mode):
(eval-after-load "foo-mode"
'(progn
(require 'bar-mode)
;; ... do other bar-mode setup here ...
))
so, in your case, you probably want to setup cedet using eval-after-load c++-mode.
You could do it like this:
(add-hook 'c-mode-common-hook (lambda ()
(load-file "~/.emacs.d/plugins/cedet/common/cedet.el")
;; any code dependent on having this file loaded
))
If loading the file (or doing the other commands) several times is a problem, you should of course first check whether this file was already loaded (either test for something defined in cedet.el, or maintain an is-loaded flag yourself).
Edit: Such a flag might look like this:
(setq need-to-load-cedet-p t)
(add-hook 'c-mode-common-hook (lambda ()
(if need-to-load-cedet-p
(progn (load-file "~/.emacs.d/plugins/cedet/common/cedet.el")
(setq need-to-load-cedet-p nil))
;; code that should only be executed once after cedet is loaded goes here
)
;; code that should be executed every time a new buffer is opened goes here
))

Emacs matlab mode key binding for running tests

I am using Emacs + matlab-mode as my Matlab development environment. I also have MTEST installed together with Matlab to run my unit tests - what I want to do now is to have a key binding that runs the tests from the current file in the matlab-shell I constantly have opened around (M-x matlab-shell).
What I have until now is:
; Runs the unit tests available in the current buffer
(defun run-matlab-test ()
(interactive)
(matlab-shell-run-command (concat "runtests "
(car (split-string (buffer-name) "\\.")))))
; Bind "C-c l" to running unit tests in matlab-mode
(defun map-run-matlab-test-keys ()
(local-set-key (kbd "C-c l") 'run-matlab-test))
(add-hook 'matlab-mode-hook 'map-run-matlab-test-keys)
What I need to do is in the run-matlab-test function to have a way of calling the runtests command with the parameter provided by the (buffer-name) command and all this should happen in the matlab shell I mentioned above. Any hints ?
Edit: I managed to get it working by calling matlab-shell-run-command. The caveat here is that it only works if the starting sequence is: open your unit-test.m file, from that file run M-x matlab-shell (this way matlab starts with the current working directory in the tests directory) and then you can use the above binding.
To avoid your caveat above, you could probably issue a cd to matlab, before calling runtest, by doing something like the following (untested):
(defun run-matlab-test ()
(interactive)
(matlab-shell-run-command (concat "cd " (file-name-directory (buffer-file-name))))
(matlab-shell-run-command (concat "runtests "
(car (split-string (buffer-name) "\\.")))))

Clojure: Converting Clojure File to YAML

How would you convert a clojure source file to YAML? I have used the clj-yaml library to do it in the interactive REPL, but I'd like to automate this, so I can pass in an input file and specify an output, ie:
clj2yaml input.clj > output.yml
As I understand it you need help to read and write the files?! See slurp and spit. For a real example of reading a YAML config file and parsing it with clj-yaml, see pswincom.gateway.config.
And here's an implementation of a simple clojure tool to do the convertion:
(ns sample
(:require [clj-yaml.core :as yaml]))
(->> (slurp (nth *command-line-args* 0))
read-string ; converts the file content to a clojure datastructure
yaml/generate-string
(spit (nth *command-line-args* 1)))
(On Windows) I can create a batch file called clj2yaml.bat to make it easy to use. It assumes the needed jar-files are located in the current directory. I'm just a novice when it comes to this kind of execution, so a better script is quite likely possible, but here it is:
java.exe -cp .\clojure-1.2.0.jar;.\clojure-contrib-1.2.0.jar;.\clj-yaml-0.3.0-20101010.033133-1.jar;.\snakeyaml-1.5.jar clojure.main sample.clj %*
I can now execute clj2yaml foo.clj foo.yaml to create the yaml file.
You already know how to code a clojure converter, you now just need to package it as a standalone application, and possibly create a sh script that just invokes your class.
As an alternative, here's a neat way to do it, if you're on a *nix environment:
#^:shebang '[
exec java -cp "$HOME/src/clj/clojure/clojure.jar" clojure.lang.Script "$0" -- "$#"
]
(your code here)