ラベル Windows の投稿を表示しています。 すべての投稿を表示
ラベル Windows の投稿を表示しています。 すべての投稿を表示

2013-11-17

コマンドのハードコーディングを回避する仕組み

/bin/sh決め打ちとかそういうのを回避するために使う。こういうの、他の人も色々書いてる気がするけど。

(defvar alternate-program-table
  (make-hash-table :test 'equal))

(defmacro define-alternate-program (program alt)
  `(puthash ,program ,alt alternate-program-table))

(defun alternate-program (program)
  (gethash program alternate-program-table))

(defadvice start-process (around kludge-for-hard-coding (name buffer program &rest program-args) activate)
  (let* ((alternate (alternate-program program))
         (program (or (if (consp alternate) (car alternate) alternate) program))
         (program-args (if (consp alternate) (append (cdr alternate) program-args) program-args)))
    ad-do-it))

こういう感じに使う。

(defmacro when-windows (&rest body)
  `(if-windows (progn ,@body)))

(when-windows
  (define-alternate-program "/bin/sh" '("fakecygpty" "/bin/sh")))

Cygwin環境とfakecygptyがちゃんとあれば、term.elのansi-termとかがWindowsでもきちんと動作するように。

2012-08-25

OCamlSpotterを強引に使うための設定

CygwinでビルドしたOCaml 4.00.0と、それを使ってビルドしたOCamlSpotter(bf0060bc031f)と、non-Cygwin Emacs 23.2を併用するためのkluge。CygwinでのパスとWindowsのパスの表現の違いによる問題を解決するものなので、MinGW版のOCamlならこういう設定は不要のはず。多分素直に使える。

.emacsの(require 'ocamlspot)以降に

(defun cygpath (args)
  (let* ((command (with-output-to-string
                    (princ "cygpath")
                    (mapc (lambda (x) (princ " ") (princ x)) args)))
         (result (shell-command-to-string command)))
    (replace-regexp-in-string "\n$" "" result)))

(defun ocamlspot-query-string-at-cursor ()
  (let ((file-name (cygpath `(-u ,(prin1-to-string (buffer-file-name))))))
    (setq ad-return-value
          (format "%s:l%dc%d"
                  file-name
                  (ocamlspot-lines-of-point)
                  (ocamlspot-bytes-of-line-to-point)))))

(defun ocamlspot-find-file-existing (path)
  (let ((path (cygpath `(-w ,path))))
    (if (file-exists-p path)
        (find-file-other-window path)
      (ocamlspot-message-add (format "ERROR: source file %s was not found" path))
      nil)))

で取り敢えず動くと思う。良く分からなかったりちゃんと動かなかったら諦めた方が吉。

やってて思ったけど、素直に仮想マシンにLinuxなりをインストールした方が苦労が少なそう。でもこのPCメモリそんな積んでないから厳しい。

2012-03-28

Chicken Schemeのビルド

WindowsでChicken Schemeをビルドするには、CygwinMinGWのどちらかのgccを使う。Visual Studioはサポートされていない。MinGWを使ってビルドする場合はMSYSは必須ではないけど、いずれにせよGNU makeは必要。以下の例はCygwinを使っている場合。

makeのマクロによって、どういった感じでビルドするか設定をする仕組み。どんなオプションがあるかはREADMEに書いてある。

% tar xf chicken-4.7.0
% cd chicken-4.7.0
% make PLATFORM=cygwin
% !! install

インストールする場所を指定しないと/usr/localにインストールされる。指定する場合はmake PLATFORM=cygwin PREFIX=/opt/chicken-4.7.0といった感じでPREFIXという名前のマクロを指定する。

2009-04-09

TRAMP

OpenSolarisをインストールしているホストのファイルを、Windows上のGNU Emacsから編集したくなったので、TRAMPを使おうと思ったところ、勢い良く落とし穴に嵌った。二度三度と嵌りたくないので、記録。

SSH経由での接続を想定。以下注意点。

  • tramp-default-methodをsshxにする
  • OpenSolaris上で実行するシェルは、/bin/shではなくて/bin/bashにする

まず、前者。GNU EmacsのWindowsバイナリからsshコマンドを起動する場合、sshの-tオプションを使わないと、仮想端末が割り当てられないので、リモートホストのシェルのプロンプトが出力されない。TRAMPはリモートホストのシェルのプロンプトの出力を待つため、こうなると処理が永遠に先に進まない。tramp-default-methodをsshxにすることで、sshが-tオプション付きで呼ばれるようになるので、この問題を避けられる。例。

(setq tramp-default-method "sshx")

次に後者。OpenSolarisの/bin/shはksh93へのシンボリックリンクだが、ksh93を使った場合、TRAMPの送るコマンドでクラッシュする。原因は、ksh上でHISTFILE変数を変更しようとすると、segmentation faultが発生するため。正直、目を疑ったが、そういう理由らしい。自分でkshを実行して同じことをしても再現率100%なので間違いない。幸い、/bin/bashが最初からあるので、代わりにこれを使う。

(require 'tramp)

(defun set-tramp-login-args (method args)
  (setcdr (assq 'tramp-login-args
                (assoc method tramp-methods))
          `(,args)))

(defun set-tramp-remote-sh (method sh)
  (setcdr (assq 'tramp-remote-sh
                (assoc method tramp-methods))
          `(,sh)))

(set-tramp-login-args "sshx" '("-e" "none" "-t" "-t" "/bin/bash --posix"))
(set-tramp-remote-sh "sshx" "/bin/bash --posix")

こんな感じ。わざわざ関数を定義しているのは、フックを使ってサーバ毎に設定の切り替えをしたかったからなんだけど、TRAMPにはそういうフックが定義されていなかった。マジですか。

Emacs 23.1付属のTRAMPでは、内部構造が変わったため、ここに書いてある設定では正常に動作しない。ksh93も、HISTFILE変数を変更したときの不具合が修正されたものを、Korn Shell 93 integration/migration projectでダウンロードできる。不具合が修正されたのが2009-06-16のリリースなので、それ以降のリリースでは問題ない。