tags:

views:

1073

answers:

1

I would like emacs to mark files that are generated as read-only when they're opened. The part of the puzzle that I'm missing is how to check if a file "exists". I currently have the following:

;;
;; get file extension
;;
(defun get-ext (file-name)
  (car (cdr (split-string file-name "\\."))))

;; 
;; get the base name of the file
;;
(defun base-name (file-name)
  (car (split-string file-name "\\.")))

;;
;; if an 'lzz' file exists for this header, mark it as read only
;;
(defun mark-read-only ()
  (if (string= (get-ext (cur-file)) "h")
      (if ( ??file-exists??? (concat (base-name (cur-file)) ".lzz") )
          (toggle-read-only))))

What can I use for "???file-exists???"?

Once I find this, I'll add "mark-read-only" to the appropriate hook (which I think is the find-file-hook).

BACKGROUND

We use lzz as a code generator to simplify our C/C++ development process. Briefly, lzz takes a single input file (which looks very like C/C++) and generates header and source files as appropriate.

By default, lzz includes #line directives so that the debugger points to the original source and not the generated source, however, to reduce compilation dependencies we normally disable these directives in header files. The result is that when debugging templates or inline functions, the debugger normally points to the generated header file and not the original source file.

This is not a big deal, however, recently I've found that when debugging I'll make a quick modification to the displayed file and then I'll rebuild. Of course this normally means that the change I made disappears because the file I edited is generated and so the changes are "blown away" during the library rebuild.

SOLUTION

Thanks to everyone for their help and comments. A special thanks to cobbal for pointing out the correct function to use.

Here's the resulting code (with updates based on the other comments here too):

(defun cur-file ()
  "Return the filename (without directory) of the current buffer"
  (file-name-nondirectory (buffer-file-name (current-buffer)))
  )

(defun mark-generated-as-read-only ()
  "Mark generated source files as read only.
Mark generated files (lzz or gz) read only to avoid accidental updates."
  (if
      (or (string= (file-name-extension (cur-file)) "h")
          (string= (file-name-extension (cur-file)) "cpp"))
      (cond
       (
        (file-exists-p (concat (file-name-sans-extension (cur-file)) ".lzz"))
        (toggle-read-only))
       (
        (file-exists-p (concat (file-name-sans-extension (cur-file)) ".gz") )
        (toggle-read-only))
       )
    )
  )
+13  A: 

try file-exists-p

"Return t if file filename exists (whether or not you can read it.)"

cobbal
Why doesn't this function appear when I do a "C-H a" appros search for it? I tried searching for file and going through the results for 'exists', and there are no matches at all for exists!
Richard Corden
yeah, I tried looking for 'exists' that way, then found the function 'find-file-existing' in files.el, opened that up and found the file-exists-p. don't know why it doesn't show up under C-H a
cobbal
file-exists-p doesn't show up under "C-H a" because it's not an "interactive" function. It should show up under "M-x apropos" though.
Edric
Which is exactly why I have this in my .emacs (define-key help-map "a" 'apropos) That way "C-h a" finds looks through all symbols for me.
Trey Jackson
Speaking of file-exists-p, this function is also a way to check if a directory exists. There is no separate directory-exists-p.
RamyenHead