* http://sosal.tistory.com/
* made by so_Sal
*/
이 포스팅에서 다루는 내용
:: DIR *opendir(const char *dirname);
:: int readdir(unsigned int fd, struct dirent *dirp, unsigned int count);
:: struct dirent{};
:: int closedir(DIR *dir);
:: int lstat(const char* path, struct stat* buf);
:: struct stat{};
:: ==================예제==================
#include<sys/types.h>
#include<dirent.h>
DIR *opendir(const char *dirname);
opendir() 함수는 매개변수 dirname에 해당하는 디렉토리 스트림을 열고,
그 디렉토리 스트림에 대한 포인터를 반환합니다.
포인터가 가리키는 디렉토리의 첫번째 항목을 가리킵니다.
#include<unistd.h>
#include<linux/dirent.h>
#include<linux/unistd.h>
int readdir(unsigned int fd, struct dirent *dirp, unsigned int count);
readdir() 함수는 파일 서술자 fd에 의해 지목된 디렉토리에서
dirp에 의해 포인트된 메모리 지역에 있는 dirent 구조체를 읽어, DIR*에 저장한다.
3번째 매개변수 count 인자는 메모리 공간의 크기이지만, 무시 가능하다.
#include<dirent.h>
dirent 구조체는 다음과 같이 선언된다.
struct dirent
{
long d_ino; /* 아이노드 */
off_t d_off; /* dirent 의 offset */
unsigned short d_reclen; /* d_name 의 길이 */
char d_name [NAME_MAX+1]; /* 파일 이름(없다면 NULL로 종료) */
}
dirent 구조체는 파일, 또는 디렉토리가 가지고 있는 정보 구조체이다.
d_ino :: 는 파일이 가지고 있는 자신만의 번호 inode를 가리키는 숫자이다.
d_off :: 는 디렉토리의 시작에서 dirent까지의 거리를 말한다.
d_reclen :: 파일 혹은 디렉토리의 이름의 길이이다. (NULL을 포함하지 않는다.)
d_name :: 파일 혹은 디렉토리의 이름이다. (NULL이라면 파일 없음을 의미)
return :: 성공 : 1, 실패 : -1.
#include <sys/types.h>
#include <dirent.h>
int closedir(DIR *dir);
closedir() 함수는 dir과 연관된 디렉토리 스트림을 닫습니다.
디렉토리 스트림 서술자 dir은 위 함수 호출 이후에는 유효하지 않습니다.
return : 성공시 0, 실패시 -1
#include<sys/types.h>
#include<sys/stat.h>
#include<unistd.h>
int stat(const char* path, struct stat* buf);
int fstat(int filedes, struct stat *buf);
int lstat(const char* path, struct stat* buf);
이 함수는 지정된 파일에 대한 정보를 반환한다. 정보를 얻기위해 필요한 접근 권한은 없지만,
파일이 위치하는 디렉토리의 읽기 권한 (탐색 권한)은 필요하다.
stat과 lstat은 동일시 되고, 경로는 절대경로, 상대경로, dirent 구조체의 d_name으로도 판별한다.
fstat은 경로가 아닌, open이나 socket, pipe 등으로 반환된
파일 서술자로 접근하는 함수이다.
struct stat
{
dev_t st_dev; /* device */
ino_t st_ino; /* inode */
mode_t st_mode; /* protection */
nlink_t st_nlink; /* number of hard links */
uid_t st_uid; /* user ID of owner */
gid_t st_gid; /* group ID of owner */
dev_t st_rdev; /* device type (if inode device) */
off_t st_size /* total size, in bytes */
blksize_t st_blksize; /* blocksize for filesystem I/O */
blkcnt_t st_blocks; /* number of blocks allocated */
time_t st_atime; /* time of last access */
time_t st_mtime; /* time of last modification */
time_t st_ctime; /* time of last change */
} //메뉴얼 페이지를 참조하였습니다.
stat 구조체입니다. 파일이 가지는 정보를 가져올 수 있도록 하는 구조체입니다.
각각의 구조체 변수들은 이름이나 간단한 주석으로 쉽게 아실거라 생각됩니다.
특히, st_mode 는 파일의 형식정보가 반환되는 변수입니다.
파일 형식과 접근 권한, 특성 등을 아래 메크로를 통해서 확인할 수 있습니다.
S_ISLNK(file_mode) //is it a symbolic link?
S_ISREG(file_mode) //regular file?
S_ISDIR(file_mode) //directory?
S_ISCHR(file_mode) //character device?
S_ISBLK(file_mode) //block device?
S_ISFIFO(file_mode) //fifo?
S_ISSOCK(file_mode) //socket?
===================================== 예제 =====================================
/*
* 리눅스/유닉스 환경에서 모든 프로세스는 파일로 되어있습니다.
* /proc 디렉토리에 자신의 pid로 디렉토리가 생성되며,
* /proc/pid/cmdline 이란 파일로부터 프로세스 이름을 알 수 있습니다.
*/
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <dirent.h>
#include <sys/stat.h>
#include <sys/types.h>
int main() {
DIR *dir; // /proc/pid/ 를 가리킬 DIR* 변수
struct dirent *entry; // 각 파일의 inode를 통해 파일을 선택할 dirent 구조체
struct stat fileStat; // 파일의 정보를 담는 구조체
int pid; // 프로세스는 /proc 디렉토리에 자신의 pid로 파일을 담아 둡니다.
char cmdLine[256];
char tempPath[256];
printf("Processes Info\n");
dir = opendir("/proc"); // /proc이란 디렉토리 스트름이 대한 포인터가 반환되었습니다.
while ((entry = readdir(dir)) != NULL) { // /proc에 존재하는 파일들을 차례대로 읽습니다.
lstat(entry->d_name, &fileStat); // DIR*가 가리키는 파일의 state 정보를 가져온다.
if (!S_ISDIR(fileStat.st_mode)) // is dir? 디렉토리인지 확인한다.
continue; // 프로세스는 /proc에 자신의 pid로 디렉토리를
// 만드는 점을 안다면 이해하실거라 생각합니다.
pid = atoi(entry->d_name); // 프로세스(디렉토리)인것을 확인하면, 숫자로 반환한다.
if (pid <= 0) continue; // 숫자가 아니라면 다시 continue;
sprintf(tempPath, "/proc/%d/cmdline", pid); // cmdline :: 프로세스 이름이 적힌파일
getCmdLine(tempPath, cmdLine); // /proc/pid/cmdline에서 프로세스의 이름을
// 가져오는 함수로 보냅니다. 아래에 정의되어있습니다.
printf("[%d] %s\n", pid, cmdLine);
}
closedir(dir);
}
int getCmdLine(char *file, char *buf) {
FILE *srcFp;
int i;
srcFp = fopen(file, "r"); // /proc/pid/cmdline에 이름이 있습니다.
memset(buf, 0, sizeof(buf));
fgets(buf, 256, srcFp);
fclose(srcFp);
}
'Linux > Linux_Source' 카테고리의 다른 글
Linux :: pwd 현재 디렉터리 경로 프로그램 소스 (4) | 2010.01.29 |
---|---|
Linux :: 간단한 Port scanner 구현하기 (2) | 2010.01.27 |
fork, pipe를 이용한 간단한 프로세스 통신 예제 (1) | 2009.12.18 |
Socket - client 소스, 다중 프로세스 채팅방 (1) | 2009.11.07 |
Socket - server 소스. 다중 프로세스 채팅방 (0) | 2009.11.07 |