Get full path of executable of running process on AIX - c

This is most similar to Get full path of executable of running process on HPUX…, except for AIX.
The basic question is: how, on AIX, can I determine the full path to the current executable? Having to do this before doing anything else (e.g., chdir) is fine.
The most accurate answer I've found so far is to check the output from
svmon -P $$ -O format=nolimit,filename=on,filtertype=client
(where $$ has its shell meaning: current pid). That's not only heavy amounts of C, but svmon is also not very fast and can easily overwhelm the runtime of the rest of the application.
The next best answer seems to be to simply look at argv[0], and, if it has a slash in it, it's either a full path name (starts with a leading /) or a relative-to-current-dir name (does not start with a leading /). If it doesn't have a slash in it, it's relative to something in PATH.
And if, after this resolution, I end up with a symlink, then there's all the resolution of symlink(s) to deal with as well (hard links are probably beyond the scope of any solution). This solution looks like it's relatively cross-platform, but is also very heavy in the C code (should be faster than svmon). And I expect there are race-conditions and such to deal with.
Thanks,
Update: I'm looking for a solution to submit to the perl devs. And they're going to worry about an insecure PATH, especially in setuid/setgid scenarios. See perlsec. I think that we could be okay here, but if you combined setuid with faking argv[0], you could force perl to think it's somewhere else, and load the wrong modules. The "next best" answer above only really works when not in perl's taint-mode.

Why can't you use ps options as a base line? Granted, you'll still need to process the cmd value to see if has a leading '/' or not. Something like
ps -o pid,env,cwd,cmd | grep youAppName | awk -f programToRationalizePathName
I don't have access to AIX anymore, but I did work on it for 2 1/2 years and I know I've used this sort of feature. I didn't think it was slow, but I might have had different requirements than you do.
I get the impression you want a utility function, a 1-at-time call that returns the full path, but if you need an on-going process and are concerned about re-starting ps every 1 minute (for example), look at the AIX specific nmon utility. Not sure if it can generate output similar to the ps -o cmd but it can be set up to run as long as you want, as often as you want (down to 1 second intervals) and it is just one process, whose output can be redirected as needed. (Nmon is not part of the std install, but most organizations do install it, as it is IBM blessed (if not supported directly)).
Of course all of the 'not 100%' caveats apply from the similar questions mentioned by you and in the comments.
I hope this helps.

Use ps to get executable path address
ps -aef | grep app | awk '{print $8}'
above command gives your app executable path address

Related

Linux: Getting Mount Point Utilization from /proc?

I know I can get mount point utilization using command line tools like df and doing something like the following:
popen("df -h /var/log | awk '{if($1==\"tmpfs\") print $5}'","r")
where the fifth column is the usage percentage.
What I want to know is if there is a way to access mount point utilization from /proc/, such as /proc/mounts. I feel that getting this information from /proc/ would be a quicker and more efficient solution than using df and awk to parse out the usage. I've searched mntent.h but couldn't find anything promising there either. Any ideas?
You probably want the statfs(2) syscall (it does not use /proc/). You probably would use it thru statvfs(3) Posix function.
Notice that the /proc/ filesystem (and also /sys/ ...) contains pseudo-files which are generated by the kernel on demand without any IO. See proc(5). You could read sequentially /proc/self/mounts and/or /proc/self/mountstats and/or appropriate files under /proc/fs/ and/or /sys/ (such as some files in /proc/fs/ext4/sda1/ or even in /sys/block/sda/sda1/ for my desktop computer ; it would be different on yours ....)
Perhaps systemd is also able to give such information, but I don't know it enough.

Control output from makefile

I'm trying to write a makefile to replace one of the scripts used in building a fairly large application.
The current script compiles one file at a time, and the primary reason for using make is to parallelise the build process. Using make -j 16 I currently get a factor of 4 speedup on our office server.
But what I've lost is some readability of the output. The compilation program for a file bundles up a few bits and pieces of work, including running custom pre-compilers, and running the gcc command. Each of these steps outputs some information, and I would prefer it to buffer the output from the command, and then show the whole lot in one go.
Is it possible to make make do this?
If you upgrade to GNU make 4.0, then you can use the built-in output synchronization feature to get what you want.
If you don't want to upgrade, then you'll have to modify each of your recipes to be wrapped with a small program that manages the output. Or you can set the SHELL variable to something that does it for you. Searching the internet should give you some examples.
A simple way to accomplish this is to send all the log output a to log directory with each file named, say:
log_file_20131104_12013478_b.txt // log_file_<date>_<time>_<sequence letter>.txt
and then simply cat them all together as your last make job in the dependency chain:
cat log_dir/log_file_20131104_12013478_*.txt > log_file_20131104_12013478.txt
With makepp this is the default behaviour as soon as you use -j. All the individual outputs (and entering dir messages) get collected and are output together as soon as the command terminates.

How to identify gnome-terminal profile?

I posted a question on askubuntu a while back. As there is no action, and I have also dug some more, I'll try here. Possibly a more correct place, (and I don't know if it is possible to move questions any more (I do not get any of those options)).
Anyhow:
Is there a way to get gnome-terminal profile ID? Need it in bash script – to do e.g. –
gconftool-2 "do some change to some value for current profile."
In my endeavour for an answer to this I have made some progress – but no satisfying solution. To be honest it truly scares me how shielded the application is from doing modifications from command line being a terminal emulator! To me it is incomprehensible.
Besides touching the source of gnome-terminal, (I do not wan a custom version), is there some legit way to get this? By the fact it is a wrapper for vte, it uses various shared libraries, some way I haven’t thought of, etc.
Add some C code into the mix is OK.
So far:
I have checked out the "save-config" option, but as it is 1. not satisfactory, aka 100%, and 2. more important this also is going to be removed it fails completely. See my own answer below for more detail.
There is no environment variable for this.
dbus: Doesn't seem to be any messages transmitted or any functions available for this kind of information. Have tested both current (3.6.0) version and latest develop.
injection: tho it is probable, and have played around with injecting custom code to it, it is such an error-prone endeavour it is not a solution.
If anyone wonder etc.
Decided to have another look at this - and made a little progress.
Using the built-in option --save-config there is these properties of interest:
Role=gnome-terminal-window-2587-1856448950-1359348087
ActiveTerminal=Terminal0xa896200
Geometry=110x87+900+1
WorkingDirectory=/home/xxx/tmp
Looking at it closer. Opened two windows in short succession and did a save-config.
Role
We can split it to the various parts:
gnome-terminal-window
2587
1856448950
1359348087
PID
2587 is same for both, and after a quick pstree 2587 -p we find it to be the PID. Further an echo $$ locates our bash (or which ever one prefer).
Time of start
Now the second number is wildly different giving a clue it is probably a random value. The last one, tho, is with only the last digit in diff. Most probably a time-stamp. I know I'm in tmp directory for this window - so, by using our knowledge of the proc file system:
# btime: boot time, in seconds since the Epoch
$ cat /proc/stat | grep ^btime | cut -d' ' -f2
1359039155
# starttime: The time in jiffies the process started after system boot.
$ cat /proc/$$/stat | cut -d' ' -f22
30893222
# WANT: 1359348087
btime + starttime / Hertz
1359039155 + (30893222 / 100) = 1359348087.22 ~ 1359348087
OK. Last digit is time-stamp on start by Epoch. But unfortunately it is not by jiffies and a rounded value so if we have started several windows by e.g. a script we can end up with same value.
(After some checking it also seems like seconds is rounded by round to nearest not towards zero etc.)
Random value
OK. So what about the value after PID? Most probably a random value, but to be sure. To check this we have to go to the source.
$ git clone git://git.gnome.org/gnome-terminal
$ gnome-terminal --version
GNOME Terminal 3.6.0
$ git log --grep="3\.6\.0"
commit f4d291a90dc4f513fc15f80fdebcdc3c3349b70a
...
Version 3.6.0
$ git checkout f4d291a90dc4f513fc15f80fdebcdc3c3349b70a
After some digging we find:
# terminal-util.c
48: void
terminal_util_set_unique_role (GtkWindow *window, const char *prefix)
{
char *role;
role = g_strdup_printf(
"%s-%d-%d-%d",
prefix,
getpid(),
g_random_int(),
(int) time (NULL)
);
gtk_window_set_role (window, role);
g_free (role);
}
OK. Not only do we confirm that the second is a random value, but also that PI and time is correct.
Geometry
xwininfo -id $(xdotool getactivewindow) | \
grep '^\s*-geometry' | \
sed 's/^\s*[^ ]* \(.*\)/\1/'
# yields 110x87+900+1
OK. Now we have three values to check against:
Time
Geometry
Path
Problem is that even with this we can easily have two windows with those values at same value. And more important; some genius has decided to remove this from the options of the application.
Terminal Window hex
Looking further at the code one find that the hex value in ActiveTerminal etc. is a pointer value to current address in memory of a struct holding current window. AKA not very usefull if one doesn't want to hack memory mappings.

Hooks on terminal. Can I call a method before a command is run in the terminal?

I am wanting to make a terminal app that stores information about files/directories. I want a way to keep the information if the file is moved or renamed.
What I thought I could do is have a function execute before any command is run. I found this:
http://www.twistedmatrix.com/users/glyph/preexec.bash.txt
But I was wondering if this would be a good way to go about it. Or should I do something else?
I would like to call that function from a C program whenever mv is entered I suppose.
If what you're trying to do is attach some sort of metadata to files, there's a much better supported way to do that -- extended attributes.
Another solution might be to use the file's inode number as an index into a database you maintain yourself.
Can you alias the mv command? in .profile or .bashrc
alias mv=/usr/bin/local/mymv
where mymv is a compiled executable that runs your C code function and calls /usr/bin/mv.
precmd and preeexec add some overhead to every bash script that gets run, even if the script never calls mv. The downside to alias is that it requires new code in /usr/local and if scripts or users employ /usr/bin/mv instead of mv it will not do what you want. Generally doing something like this often means there is a better way to handle the problem with some kind of service (daemon) or driver. Plus, what happens if your C code cannot correctly handle interesting input like
mv somefille /dev/null
If you want to run command each time after some command was executed in the terminal, just put the following in ~/.bashrc:
PROMPT_COMMAND="your_command;$PROMPT_COMMAND"
If you want your command to be executed each time before mv is executing, put the following in ~/.bashrc:
alias mv="your_script"
Make sure that your script will execute real mv if needed.
You can use inotify library to track filesystem changes. It's good solution, but once user remove file, it's already gone.
You might be able to make use of the DEBUG trap in Bash.
From man bash:
If a sigspec is DEBUG, the command arg is executed before every
simple command, for command, case command, select command, every
arithmetic for command, and before the first command executes in
a shell function
I found this article when I was forced to work in tcsh and wanted to ensure a specific environemtn variable was present when the user ran a program from a certain folder (without setting that variable globally)
tcsh can do this.
tcsh has special alias, one of which is precmd
This can be used to run a script just before the shell prompt is printed.
e.g. I used set precmd 'bash $HOME/.local/bin/on_cd.sh'
This might be one of the very few useful features in csh.
It is a shame but I don't think the same or similar feature is in bash or other sh derivites (ash, dash etc). Related answer.

Recording command line input and output on linux with C

Basically I want to do a program almost like a keylogger. The thing is that I as network admin sometimes I don't remember what I did to a machine on certain case, or same times I make howto's and tutorials for linux. I want to record what have i done.
So basically the idea of this program is:
you type the name of the program, (I call it rat for the moment)
$ rat
Welcome everything from now on will be recorded
recording $ ls
file1 file2 file3
recording $ quit
Bye bye
Everything you do will go out to an xml file. Something like this
<?xml version='1.0' encoding='UTF-8' ?>
<rat>
<command>
<input>ls</input>
<output>file1 file2 file3</output>
<err><err>
</command>
</rat>
i am doing some tests with fp_in = popen( input, "w");
and system, but first with popen i cant change directories and with "system i cant properly manage the input and output.
I was also checking if there is something I can do to bash like a plugin but haven't find any information.
At some points if feels like it I should create another shell (which is way beyond my current abilities) or fork bash sh. But it should been that complicated right.
I am open to suggestion where to start.
I am rusty with C, so I am reading again a lot of basic stuff.
With the xml file, later i was thinking on making a program to store this data and/or editing this data so i can create tutials and howto.
I can think of many ways of expanding this up to using printscreen so all the stored images go to a file you can upload to a server (for the moment i am glad to store the data). It could be a usefull tool.
ps. I do know this can be use for evil things too.
There already exists the script command, which will record all input and output into the terminal, writing it into a transcript. I would recommend just using that, unless you have particular needs that it doesn't meet. Actually, the nicest version of script that I've seen has been the NetBSD version, so you may want to look into that if the Linux version doesn't meet your needs.
If you would like to write it yourself, instead of using system, I would recommend that you use fork/exec to create a single shell process, which you copy all input and output into. To get an idea of how this works, I'd recommend looking at the source code for an existing version of script.
Most shells have a script built-in which will simply record the text in- and out- from the command line. Not quite what you're looking for... To my surprise script is not a built in, which means it is a model for building what you want.
The script command does almost what you want: it simply records the text in- and out- from the command line.
If you make your prompt distinctive (so that you can reliably tell the difference between shell commands and everything else) you can post-process the output of script to achieve your goals. Alternately you can hack script to get it to emit the XML you're looking for.
You can also try approaching this from a different angle. Instead of using a regular shell, connect to the machine using ssh or telnet and run your commands that way. Many ssh/telnet clients (PuTTY, for instance) have an option to log all console input and output during the session. You should be able to post-process this log to generate whatever type of logfile that you need.
Depending on your setup, you might not even have to use a second machine (you should be able to ssh into yourself).

Resources