无名师与MCSE能者 一通熟Windows之能者见无名师,曰:“闻师深修Unix之道,吾以密巧相述,相益,可乎?” 无名师曰:“求智,善矣;然Unix之道并无甚密巧。” 能者惑:“人曰师乃当世Unix大道之贤者,通晓其中之变法,如吾之于Windows;吾乃MCSE,有世所罕之证书,吾铭记各注册表项功能于心,更可细述任一Windows API,乃至微软所未曾详述者。师,所以为师,为智,皆揭而知他人之不知也。” 无名师曰:“怠矣,本无秘,何以揭?” 能者嗔:“若无密巧,何以修乃成师之业?” 无名师曰:“求智者,以他人之不知为智,犹如求光明者,拥烛笼火,以为珍贵,乃终被灼也。” 听此,能者顿觉灵光。 Master Foo and the MCSE Once, a famous Windows system administrator came to Master Foo and asked him for instruction: “I have heard that you are a powerful Unix wizard. Let us trade secrets, that we may both gain thereby.” Master Foo said: “It is good [...]
此前的笔记《Linux程序已运行实体的检测以及其PID的获得》通过Linux里面的bash命令来获取正在运行的同名进程的pid,正如网友AzureSky提醒说实际上平常此类程序所用的方法都是文件锁,比如dhclient、apt-get系列、pacman诸如此类,都是通过往/var/run里面写入一个包含自身pid的xx.pid文件,同时加上排他锁,只要当前进程还在,新的进程就不可能再加锁,也就能检测出是否单实例了。(AzureSky博客另外整理出APUE的一个实现) 至于后台运行,都是通过fork来生成新进程,虽然还需要setsid等的调用以确保子进程正常运行,不过这里暂不详细讨论,重点关注文件排他锁和生成的后台进程的“规范方法“(参考《Unix环境高级编程 APUE 第二版》)。 整个过程是这样的: 打开文件; 获得该文件的锁的状态; 如果没有锁,则给该文件加上自己的锁并写入自己的pid*;否则获得锁着该文件的进程的pid 如果能够顺利加上锁,则生成子进程;子进程等待父进程退出后马上给文件加上自己的锁; *其实写不写入pid对整个过程影响不大,只是惯例如此。 过程并不复杂,纠结的地方就是,文件锁是针对进程而言的,在生成后台进程的过程中,父进程和子进程虽然说拥有共同的文件描述字之类的资源,但由于是两个完全不同的进程,文件锁并不会继承过去。只有当父进程完全退出,失去对文件的锁操作后,子进程才能重新获得锁。 文件锁的调用fcntl函数的cmd参数里面有F_SETLK和F_SETLKW两个,后者是阻塞式的调用,就非常适合上述子进程等待父进程退出以获得锁的情形。 PT根据《APUE 2nd》F14.5、F14.6 整理出来的一份示例代码: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 [...]
Page optimized by WP Minify WordPress Plugin