On a Linux system (the one in front of me is an Ubuntu 10.04, but that shouldn't matter), how can I tell which of two files created within the same second was created first? The process I control creates neither itself; in all other respects the ctime would, I think, do the trick, but the 1 second resolution is a problem.
For background, I'm trying to reliably determine whether a potentially stale pidfile refers to the current process with that pid. If there's a better way to do that, I'm all ears.
Actually, on modern Unices with modern filesystems, the file modification time is stored in a timespec. Details:
The standard says stat looks like this WRT times:
struct timespec st_atim Last data access timestamp.
struct timespec st_mtim Last data modification timestamp.
struct timespec st_ctim Last file status change timestamp.
And a timespec
time_t tv_sec seconds
long tv_nsec nanoseconds
So, doing a stat on my Linux 2.6.39:
Access: 2011-07-14 15:38:20.016666721 +0300
Modify: 2011-06-10 03:06:12.000000000 +0300
Change: 2011-06-17 11:01:35.416667110 +0300
In conclusion, I think you've got enough precision there if the hardware is supplying it.
You can try ls -rt to sort the files by time on the hope that the file header has more precision than the default list time format displays. But if the file system doesn't have the information, there is no way to do this.
Other options? You could add an ID to the file and always increment it but as soon as you try to load this ID from the file system (when you create a new process), you'll run into problems with locking.
So how can you make sure the PID file is not stale? Answer: Use the daemon script. It runs a process in the background and makes sure the PID file gets deleted as soon as the process exits.
Related
How can I lock a file in Linux with a filestream?
Creating a filestream like in the example below works perfectly in Windows, the file is locked and cannot be deleted or written to in other sessions until the stream is freed. Under Linux I can delete the file or write to it in an other session without any problems.
var f: TFileStream;
...
f := TFileStream.Create(TPath.Combine(FTemp, lowerCase(Name)), fmOpenReadWrite + fmCreate);
...
NEW FINDINGS 1.1.2020
Linux does not automatically apply an atomic lock on files like Windows does. So I tried applying a lock after creating the file:
function flock(handle, operation: integer): integer; cdecl; external libc name _PU + 'flock';
const
LOCK_EX = 2;
...
f := TFileStream.Create(fn, fmCreate, fmShareExclusive);
flock(f.handle, LOCK_EX);
There is a small race condition as creating the file and locking it is not one single step but for my application this is not a problem. When looking at the created lock file on the linux console the difference is obvious:
Wihout flock():
mint#minti:/tmp/itclock$ lsof wirsing
COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME
_TestLibB 5417 mint 14u REG 8,1 8 2755101 wirsing
With flock():
mint#minti:/tmp/itclock$ lsof wirsing
COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME
_TestLibB 6365 mint 14uW REG 8,1 0 2755117 wirsing
The difference is the big W that indicates an exclusive lock.
Unfortunately this does not solve the problem as creating a second filestream just creates a second exclusive lock in the same process and deleting the file from an other process is still possible. If there was a way to read the extended attributes of lsof <file> from within delphi ...
An other finding (new year, new ideas)
As I run my tests as unit tests and create several objects in the same process to test the locks this might be the cause as Windows does not allow accessing the locked file even from within the same process. This seems to be different in Linux. I need something that behaves like in Windows - it should be no difference if it is locked in a different process or a thread of the same process. Perhaps Linux offers a totally different way to accomplish such a locking mechanism?
And still: Any help is very appreciated!
Finally I found a usable solution that at least serves my requirements:
In Windows I continue using the simple approach with fmShareExclusive. In Linux I apply a FileLock as described above in the question. For checking the exclusive lock I run a command line via popen and capture the result prior to deleting the lock file and then creating/locking it.
lsof -Fl <my flock file name>
This outputs three lines if a Lock exists:
p7590
f14
lW
I look for lW in the result that indicates an exclusive lock on the file and I can react on that as required.
This solution still works if a process crashes as then the file lock will be gone too.
I am aware of the fact that this is not a very elegant solution but it seems to be rubust and reliable enough.
Comments and suggestions are very welcome!
I find a lot documents about psacct, but they are addressing usage, not how it works.
Question
I really want to know how process accounting works:
Which part of the system records information about processes?
How does it work?
Already done
I installed psacct on RHEL 6.5.
The service staring script actually (/etc/init.d/psacct) call this:
/sbin/accton $ACCTFILE
The /sbin/accton calls system call acct()
man acct
DESCRIPTION
The acct() system call enables or disables process accounting. If called with the name of an existing file as its argument, accounting is
turned on, and records for each terminating process are appended to filename as it terminates. An argument of NULL causes accounting to be
turned off.
The answer to your question is in the linux source file kernel/acct.c. Particularly in the fill_ac function
/*
* Write an accounting entry for an exiting process
*
* The acct_process() call is the workhorse of the process
* accounting system. The struct acct is built here and then written
* into the accounting file. This function should only be called from
* do_exit() or when switching to a different output file.
*/
static void fill_ac(acct_t *ac)
fsStat class instance returns mtime, atime and ctime date objects, but there seems to be API only for changing mtime and atime (last modification and access i guess). How can i change creation time to create exact copy of file as it'd be also created the same time as original one?
It's not possible at present with Node itself, but you can use https://github.com/baileyherbert/utimes (a native add-on for Node) to change the creation time (aka btime) of a file on Windows and Mac.
tl;tr: That's not possible atm (Node.js <= v6).
Even though, fs.stat() returns the birthtime of files:
birthtime "Birth Time" - Time of file creation. Set once when the file is created. On filesystems where birthtime is not available, this field may instead hold either the ctime or 1970-01-01T00:00Z (ie, unix epoch timestamp 0)…
Prior to Node v0.12, the ctime held the birthtime on Windows systems. Note that as of v0.12, ctime is not "creation time", and on Unix systems, it never was.
Updating is not possible. From https://github.com/joyent/node/issues/8252:
fs.utimes uses utime(2) (http://linux.die.net/man/2/utime), which doesn't allow you to change the ctime.
(Same holds for birthtime)
The fs.utimes and fs.utimesSync methods are built into Node.js core. See https://nodejs.org/api/fs.html#fs_fs_utimes_path_atime_mtime_callback
Note:
The value should be a Unix timestamp in seconds. For example, Date.now() returns milliseconds, so it should be divided by 1000 before passing it in.
To convert a JS Date object to seconds:
new Date().getTime()/1000|0
I am in a kernel module and I want to have the whole process name
from a given pid. exactly: I want the line which is hold in /proc/PID/cmdline.
The problem is that task_struct->comm[] is only 15 bytes long and doesn't handle
if a program changes his argv[] manually or via setproctitle(3)...
Any ideas? :)
You could always look at how the kernel does it. You'll see the function:
proc_pid_cmdline(struct task_struct *task, char * buffer)
It's fairly easy to follow but once you have the task_struct for the process you are interested in you use access_process_vm() to slurp the bits you want from mm->arg_start.
What's wrong with opening the /proc/<pid>/cmdline file and just reading the contents?
Is there any way to store file creation time in linux? May be filesystem that supports that. I mean CREATION TIME not mtime or ctime.
Most (all?) Linux filesystems do not store the time when the file was created. Instead, they just store when the file was last modified, when it was last accessed, and when it last had an administrative action applied to it (e.g., changing its permissions). Of those, the best approximation to what you're looking for is usually the modification time.
I do believe that Ext4 has creation time support.
Try this debugfs:
debugfs -R 'stat <inode>' /dev/block_dev.
Fragment: Address: 0 Number: 0 Size: 0
ctime: 0x51872d50:df6167a0 -- Mon May 6 07:10:56 2013
atime: 0x5183b4e1:d2ad63cc -- Fri May 3 16:00:17 2013
mtime: 0x51872d50:df6167a0 -- Mon May 6 07:10:56 2013
crtime: 0x5183b4e1:d2ad63cc -- Fri May 3 16:00:17 2013
Understanding EXT4 (Part 2): Timestamps
On NTFS using ntfs-3g you can access the creation time via an extended attribute (see attr(5)).
If you want to store file creation times, you can use filesystem event notification tool like inotify.
It has system calls that make you aware of IN_CREATE (a file creation event) or some other event, When a file creation event happens you can simply log that with current time in a file of your preference.