2014-06-02 :-(
_ 午後
1300 検討
_ [NetBSD][/bin/pwd][pwd][コードリーディング]NetBSD /bin/pwd を読む
ソース bin/pwd/pwd.c
マニュアル pwd - NetBSD Manual Pages
使用例
% pwd -L /home/rin/public_html/diary
シンボリックリンクを解決する
% pwd -P /home/rin/public_html/tdiary-core
処理の流れ
main getcwd または getcwd_logical
読む。
冒頭に嘆きの声
/* * Note that EEE Std 1003.1, 2003 requires that the default be -L. * This is inconsistent with the historic behaviour of everything * except the ksh builtin. * To avoid breaking scripts the default has been kept as -P. * (Some scripts run /bin/pwd in order to get 'pwd -P'.) */
「仕様では -L がデフォルトなんだけど、互換性のために -P 残しとくわ」
main() を読む
// pwd -L された場合 if (lFlag) p = getcwd_logical(); // それ以外では NULL にしておく else p = NULL; // -L ではない場合はこっち。つまりデフォルト if (p == NULL) p = getcwd(NULL, 0);
-P またはオプションなしの場合は getcwd を呼ぶ getcwd(3) - NetBSD Manual Pages
getcwd_logical を読む。-L された場合にこっちにくる。論理 PATH というらしんだが相対 PATH のことでいいんだろか。
static char * getcwd_logical(void) { char *pwd; struct stat s_pwd, s_dot; // 環境変数 $PWD を使う // 正確だし高速だし /* Check $PWD -- if it's right, it's fast. */ pwd = getenv("PWD"); if (pwd == NULL) return NULL; // root からの PATH だった場合は返る if (pwd[0] != '/') return NULL; // こういう PATH も返る if (strstr(pwd, "/./") != NULL) return NULL; if (strstr(pwd, "/../") != NULL) return NULL; // stat を取得できない場合も返る if (stat(pwd, &s_pwd) == -1 || stat(".", &s_dot) == -1) return NULL; // 現在地と . が一致しなければ返る if (s_pwd.st_dev != s_dot.st_dev || s_pwd.st_ino != s_dot.st_ino) return NULL; // 相対 PATH が返る? ./ みたいな? return pwd; }