Tcl: [file tempdir] - directory

Somehow in tcl 8.6:
file tempdir - is missing
file tempfile - is present
Question: why there is no tempdir ?

There's no file tempdir because there wasn't a sufficiently pressing need for someone to code it up, whereas temporary files are much more pressing (and harder to get right, especially across operating systems). You can always use tcllib as well as Tcl as they're under identical licenses; that library of Tcl-scripted packages provides a fileutil package that has this command:
set dirname [fileutil::maketempdir]
which should be plenty adequate. (There's a bunch of options available to cover most needs.)

A pattern without fileutil dependency:
proc ::util::tempdir {template} {
close [file tempfile path $template]
file delete $path
file mkdir $path
return $path
}

What I did:
set workdir [exec mktemp -d]
Note: this depends on an external binary mktemp. I think this should work on anything UNIX-y.

Related

GNU-Make: how to copy files from source to destination

I know this is a basic question but I'm missing something fundamental about makefiles.
Take this simple rule/action:
doc: ${SRC_DIR}/doc/dir1/file1.pdf ${SRC_DIR}/doc/dir1/file2.pdf
cp $? ${DEST_DIR}/doc/
the first time I run it, it copies file1.pdf and file2.pdf to the destination/doc directory. Perfect. I'm expecting the next time I run it, for it to do nothing. The source files haven't changed, aren't they a dependency? But when I run I get :
cp : cannot create regular file ..... :Permission denied.
so, 2 questions:
1) Why is it trying to do it again? When I run make -d I see it eventually says: No need to remake target .../file1.pdf and .../file2.pdf but then
it says : must remake target 'doc'
If it doesn't need to make either pdf file, why does it need to make doc?
2) say the pdf files had changed in the source, they are read only though, so it gets the permission denied error. How do you get around this?
A make rule:
target: preqreq0 prereq1...
command
...
says that target needs to be (re)made if it does not exist or is older than
any of the prerequisites preqreq0 prereq1..., and that target shall be
(re)made by running the recipe command ....
Your rule:
doc: ${SRC_DIR}/doc/dir1/file1.pdf ${SRC_DIR}/doc/dir1/file2.pdf
cp $? ${DEST_DIR}/doc/
never creates a file or directory doc, so doc will never exist when
the rule is evaluated (unless you create doc by other means), so the recipe
will always be run.
The kind of target that I believe you want doc to be is a phony target,
but you are going about it wrongly. A reasonable makefile for the purpose would
be:
SRC_DIR := .
DEST_DIR := .
PDFS := file1.pdf file2.pdf
PDF_TARGS := $(patsubst %,$(DEST_DIR)/doc/%,$(PDFS))
.PHONY: doc clean
doc: $(PDF_TARGS)
$(DEST_DIR)/doc/%.pdf: $(SRC_DIR)/doc/dir1/%.pdf
cp $< $#
clean:
rm -f $(PDF_TARGS)
I recommend The GNU Make documentation
As for your second problem, how to overwrite "readonly" files, it is unrelated to make.
You cannot overwrite files to which you do not have write permission, regardless
of the means by which you try to do it. You must get write permission to any files
that you need to write to. It is a system administration matter. If you do not
understand file permissions you may find help at sister-site Unix & Linux
or serverfault

Creating a terminal command in Minix

I want to create a command that runs an executable created by compiling a c program. I couldn't find a proper solution. Let's say I have a file named myprogram.c and compile it and have myprogram as . I want to type myprogram in any folder in my system and run it. How can I achieve this?
First find out what your PATH is
echo $PATH
For you this outputs
/sbin:/usr/sbin:/bin:/usr/bin:/usr/pkg/sbin:/usr/pkg/bin/usr/X11R7/bin:usr/X11R‌​‌​6/bin:/usr/local/sbin:/usr/local/bin
Then assuming your program is in the /usr/myprog directory, append /usr/myprog to your PATH (don't forget to separate directories with a colon :)
export PATH=/sbin:/usr/sbin:/bin:/usr/bin:/usr/pkg/sbin:/usr/pkg/bin/usr/X11R7/bin:usr/X11R‌​‌​6/bin:/usr/local/sbin:/usr/local/bin:/usr/myprog
Doing this tells the system when you don't specify an absolute path (like ./myprogram) to look in all the directories in PATH. It is good to add the absolute path of your executable to PATH because adding . to your PATH is frowned upon by some (see this question).
You have to add it in your PATH from your shell rc file
You place the executable into a directory that your shell already searches for programs, or you add your program's location to that list.
the $PATH environment variable contains this information. You can add myProgram's location to it, i.e. export PATH=$PATH:/new/dir, or just print out $PATH and copy myProgram into one of the paths listed there already.

What are #file# and file~ and how can I get rid of them?

I originally had three files: makefile, readme.txt, and hashtable.c in my directory, where I am writing my code in emacs. I noticed that some new files: #hashtable.c#, #readme.txt#, hashtable.c~, and makefile~ have been created. I was wondering what these files were. Are these important, and if not, how do I tell emacs to stop making them? I'm also curious why readme.txt doesn't get a tilde file and makefile doesn't get a sharp file.
The file with the ~ is a backup file that automatically gets created when you save a file. The #readme.txt# is the file being currently edited/in use (i.e., the autosave version). That will usually go away (unlike the ~ file) when you exit emacs normally (if it crashes or gets killed the # files may stay around).
You might find this page about emacs backup files of interest, and this SO question: How do I control how Emacs makes backup files?
You can prevent backup files from being created with this:
(setq make-backup-files nil)
I recommend installing no-littering. It automatically puts backup files (file~) in ~/.emacs.d/var/backup/. It doesn't do anything about autosaves (#file#), but there is a note about putting those files in a specified directory in the README:
(setq auto-save-file-name-transforms
`((".*" ,(no-littering-expand-var-file-name "auto-save/") t)))
Neither of these things actually prevents Emacs from creating these files, but I'm assuming most people actually want these files (in case of a crash), but don't want them strewn all over the filesystem.
For #files# you have to do rm "#file#" from the terminal, because rm #file# doesn't work.
For ~file you can simply digit rm ~file.
Maybe you could try:
find . -name \\#*\\# | xargs rm
Warning: this will remove those files matching in subdirectories.

zsh doesn't complete local dir name when trying to execute local executable

I have a local directory with executable in it (e.g. foo_dir/bin/bar). I typed "foo", but foo_dir wasn't suggested. What cames out is other program in $PATH (such as bootlogd).
How should I config my zshrc? Thanks
I think adding "." to your $PATH variable will fix this issue. By default $PATH contains standard bin directory i.e /usr/bin, /bin, /usr/local/bin.
I found a workable solution, by "setopt autocd", but the side effect is when executing some directory, you'll cd into it.

How do I get vim's :sh command to source my bashrc?

Whenever I start a shell in vim using :sh, it doesn't source my ~/.bashrc file. How can I get it to do this automatically?
See :help 'shell'. You can set this string to include -l or --login, which will source your .bashrc file. So, you might have a line like this in your .vimrc:
set shell=bash\ --login
Note that this will alter everything that invokes the shell, including :!. This shouldn't be much of a problem, but you should be aware of it.
The value of this command can also be changed by setting the $SHELL environment variable.
If it doesn't source your .bashrc file, it may still source your .bash_profile file. I usually make one of them a symlink to the other. If your .bashrc performs some particularly odd one-time operations, you may have to edit it to only perform those operations with a login shell, but I've never had problems with it.
~/.vimrc
cmap sh<CR> !bash --login<CR>
If you quickly enter "sh<Enter>" in command-line, you can start bash with sourcing ~/.bashrc. So dirty.

Resources