您的位置:首页 > 移动开发 > Android开发

make ls and chmod command on android device

2016-06-03 19:14 381 查看

前言

做了一个练习,实现ls命令和chmod命令. 用c实现,用make编译.

在真机上测试过了,好使.

效果图



makefile文件

#测试用make命令行编译makefile, 用来产生在真机中可以运行的android-linux程序
#用法
# make 显示帮助
# make clean => 清除垃圾
# make all => 重新建立工程所有输出文件

#规则需要的依赖文件(.o, .c, .cpp, .h) 需要在规则:符号后列出, 多个依赖文件之间用' '空格符号分隔, 换行用'\'
#------------------------------------------------------------
#定义变量, 必须在变量被用到之前, 提前定义
#------------------------------------------------------------
NDK_ROOT_DIR := D:/android-ndk-r10e
NDK_PLATFORMS_DIR := $(NDK_ROOT_DIR)/platforms
NDK_TOOLCHAINS_DIR := $(NDK_ROOT_DIR)/toolchains

NDK_PLATFORMS := $(NDK_PLATFORMS_DIR)/android-19/arch-arm/usr
NDK_PLATFORMS_INC := $(NDK_PLATFORMS)/include
NDK_PLATFORMS_LIB := $(NDK_PLATFORMS)/lib

NDK_PREBUILT := $(NDK_TOOLCHAINS_DIR)/arm-linux-androideabi-4.9/prebuilt/windows
NDK_PREBUILT_INC := $(NDK_PREBUILT)/lib/gcc/arm-linux-androideabi/4.9/include-fixed

CRT_BEGIN_IMP := $(NDK_PLATFORMS_LIB)/crtbegin_dynamic.o
CRT_END_IMP := $(NDK_PLATFORMS_LIB)/crtend_android.o

NDK_GCC_PROG := $(NDK_PREBUILT)/bin/arm-linux-androideabi-gcc.exe

COMPILER_OPTIONS := \
-I$(NDK_PREBUILT_INC) \
-I$(NDK_PLATFORMS_INC) \
-L$(NDK_PLATFORMS_LIB) \
-nostdlib \
-Bdynamic \
-lc \
-lgcc

#------------------------------------------------------------
# 终极目标 : 第一个规则名称是终极目标
# 帮助
#------------------------------------------------------------
no_make_paramter:
@echo usage:
@echo make all : build all
@echo make clean : remove trash
@echo make install : install elf file to /data/local/tmp
@echo make run : run elf file on the device

#------------------------------------------------------------
#被依赖的.o 编译规则
#------------------------------------------------------------

#------------------------------------------------------------
# hw.c
#------------------------------------------------------------
HW_O_IMP := hw.c
HW_O_OUT := hw_c.o
$(HW_O_OUT): $(HW_O_IMP)
$(NDK_GCC_PROG) \
$(COMPILER_OPTIONS) \
-c $(HW_O_IMP) \
-o $(HW_O_OUT)

#------------------------------------------------------------
# 因为定义变量后,有执行的先后顺序, 必须执行 make all 才能到这
#------------------------------------------------------------
#工程最终输出文件名称, 测试过了, 可以改成自己想要的
PRJ_OUT := hw
OBJECTS := $(HW_O_OUT)

all: $(OBJECTS)
$(NDK_GCC_PROG) \
$(COMPILER_OPTIONS) \
$(HW_O_OUT) \
$(CRT_BEGIN_IMP) \
$(CRT_END_IMP) \
-o $(PRJ_OUT)

#------------------------------------------------------------
# 伪目标
# make clean : 清除垃圾
#------------------------------------------------------------
.PHONY:clean
clean:
cls
del $(HW_O_OUT)
del $(PRJ_OUT)

#------------------------------------------------------------
# make install : 安装
#------------------------------------------------------------
install:
adb devices
adb push $(PRJ_OUT) /data/local/tmp
adb shell chmod 700 /data/local/tmp/$(PRJ_OUT)

#------------------------------------------------------------
# make run : 运行
#------------------------------------------------------------
run:
#   adb shell /data/local/tmp/$(PRJ_OUT)
adb shell


实现

#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <pwd.h>
#include <sys/stat.h>
#include <string.h>
#include <errno.h>
#include <time.h>
#include <dirent.h>

#define LINE "============================================================"
#ifndef BOOL
#define BOOL int
#define TRUE 1
#define FALSE 0
#endif // #ifndef BOOL

#ifndef NULL
#define NULL 0
#endif // #ifndef NULL

void fn_help();
void fn_do_task(int argc, char** argv);

void fn_parse_cmd(int argc, char** argv);
BOOL fn_cmd_process_ls(int argc, char** argv);

BOOL fn_cmd_process_ls_file(char* szFileName);
BOOL fn_cmd_process_ls_dir(char* pcDirName);

BOOL fn_cmd_process_chmod(int argc, char** argv);

int main(int argc, char** argv) {
printf("hw_cmd v0.0.1.12\r\n");
fn_parse_cmd(argc, argv);

/**
./hw_cmd ls ccc
argc = 3 argv[0] = ./hw_cmd argv[1] = ls argv[2] = ccc

./hw_cmd chmod 775 cc
argc = 4 argv[0] = ./hw_cmd argv[1] = chmod argv[2] = 775 argv[3] = cc
*/
switch (argc) {
case 3:
case 4:
fn_do_task(argc, argv);
break;
default:
fn_help();
}

return 0;
}

void fn_do_task(int argc, char** argv) {
if (fn_cmd_process_ls(argc, argv)) {
return;
} else if (fn_cmd_process_chmod(argc, argv)) {
return;
} else {
fn_help();
}
}

BOOL fn_cmd_process_ls(int argc, char** argv) {
struct stat _stat;

/**
./hw_cmd ls ccc
argc = 3 argv[0] = ./hw_cmd argv[1] = ls argv[2] = ccc
*/
if ((3 != argc) || (0 != strcmp(argv[1], "ls"))) {
return FALSE;
}

printf("process ls <%s>\r\n", argv[2]);

if (0 == stat(argv[2], &_stat)) {
if (S_ISDIR(_stat.st_mode)) {
fn_cmd_process_ls_dir(argv[2]);
} else if (S_ISBLK(_stat.st_mode) || S_ISCHR(_stat.st_mode)) {
fn_cmd_process_ls_file(argv[2]);
}
} else {
printf("stat error : %s\r\n", strerror(errno));
}

return TRUE;
}

BOOL fn_cmd_process_ls_file(char* szFileName) {
struct stat _stat;
int iRc = 0;
struct passwd* _passwd = NULL;
struct passwd* _passwd_g = NULL;
struct tm _tm;
char* pcFileName = NULL;
char szBufSize[260] = {'\0'};
// struct tm* gmtime( const time_t* timer );

iRc = stat(szFileName, &_stat);
if ((0 == iRc) && (0 != _stat.st_size)) {
/*
printf("\r\n\r\n_stat.st_mode = %d\r\n", S_ISBLK(_stat.st_mode));
printf("_stat.st_mode = %d\r\n", S_ISCHR(_stat.st_mode));
printf("_stat.st_mode = %d\r\n", S_ISDIR(_stat.st_mode)); ///< 目录
printf("_stat.st_mode = %d\r\n", S_ISFIFO(_stat.st_mode));
printf("_stat.st_mode = %d\r\n", S_ISLNK(_stat.st_mode));
printf("_stat.st_mode = %d\r\n", S_ISREG(_stat.st_mode)); ///< 文本
printf("_stat.st_mode = %d\r\n", S_ISSOCK(_stat.st_mode));
*/

_passwd = getpwuid(_stat.st_uid);
_passwd_g = getpwuid(_stat.st_gid);
localtime_r(&_stat.st_atime, &_tm);
pcFileName = strrchr(szFileName, '/');

if ((0 == _stat.st_size) || S_ISDIR(_stat.st_mode)) {
sprintf(szBufSize, "%8c", ' ');
} else {
sprintf(szBufSize, "%8lld", _stat.st_size);
}

printf("-%s%s%s%s%s%s%s%s%s %-8s %-8s %s %4.4d-%2.2d-%2.2d %2.2d:%2.2d %s\r\n",
(_stat.st_mode & S_IRUSR) ? "r" : "-",
(_stat.st_mode & S_IWUSR) ? "w" : "-",
(_stat.st_mode & S_IXUSR) ? "x" : "-",

(_stat.st_mode & S_IRGRP) ? "r" : "-",
(_stat.st_mode & S_IWGRP) ? "w" : "-",
(_stat.st_mode & S_IXGRP) ? "x" : "-",

(_stat.st_mode & S_IROTH) ? "r" : "-",
(_stat.st_mode & S_IWOTH) ? "w" : "-",
(_stat.st_mode & S_IXOTH) ? "x" : "-",

(NULL != _passwd) ? _passwd->pw_name : "unknown",
(NULL != _passwd_g) ? _passwd->pw_name : "unknown",
szBufSize,

1900 + _tm.tm_year,
_tm.tm_mon,
_tm.tm_mday,
_tm.tm_hour,
_tm.tm_min,

(NULL != pcFileName) ? (pcFileName + 1): szFileName);
}

return TRUE;
}

BOOL fn_cmd_process_ls_dir(char* pcDirName) {
DIR* dirp;
struct dirent* direntp;
char szBuf[260] = {'\0'};

dirp = opendir(pcDirName);
if( dirp == NULL ) {
sprintf(szBuf, "can't open dir <%s>, %s\r\n",
(NULL != pcDirName) ? pcDirName : "",
strerror(errno));
printf(szBuf);
} else {
for(;;) {
direntp = readdir( dirp );
if( direntp == NULL ) break;

if ((0 == strcmp(".", direntp->d_name))
|| (0 == strcmp("..", direntp->d_name))) {
continue;
}

sprintf(szBuf, "%s/%s", (NULL != pcDirName) ? pcDirName : "", direntp->d_name);
fn_cmd_process_ls_file(szBuf);
}

closedir( dirp );
}

return TRUE;
}

BOOL fn_cmd_process_chmod(int argc, char** argv) {
/**
./hw_cmd chmod 775 cc
argc = 4 argv[0] = ./hw_cmd argv[1] = chmod argv[2] = 775 argv[3] = cc
*/

int i_access_permissions = 0;
int i_access_permissions_owner = 0;
int i_access_permissions_group = 0;
int i_access_permissions_other = 0;
mode_t mode = 0;
char szBuf[260] = {'\0'};

if ((4 != argc) || (0 != strcmp(argv[1], "chmod"))) {
return FALSE;
}

printf("process chmod <%s> <%s>\r\n", argv[2], argv[3]);
i_access_permissions = atoi(argv[2]);

i_access_permissions_other = i_access_permissions % 10;
i_access_permissions = (i_access_permissions - i_access_permissions_other) / 10;

i_access_permissions_group = i_access_permissions % 10;
i_access_permissions = (i_access_permissions - i_access_permissions_group) / 10;

i_access_permissions_owner = i_access_permissions;

/*
// process chmod <765> <test_file>
// permissions is 7,6,5

printf("permissions is %d,%d,%d\r\n",
i_access_permissions_owner, i_access_permissions_group, i_access_permissions_other);
*/

// 设置访问权限-所有者
if (i_access_permissions_owner & 4) {
mode |= S_IRUSR;
}

if (i_access_permissions_owner & 2) {
mode |= S_IWUSR;
}

if (i_access_permissions_owner & 1) {
mode |= S_IXUSR;
}

// 设置访问权限-组
if (i_access_permissions_group & 4) {
mode |= S_IRGRP;
}

if (i_access_permissions_group & 2) {
mode |= S_IWGRP;
}

if (i_access_permissions_group & 1) {
mode |= S_IXGRP;
}

// 设置访问权限-其它用户
if (i_access_permissions_other & 4) {
mode |= S_IROTH;
}

if (i_access_permissions_other & 2) {
mode |= S_IWOTH;
}

if (i_access_permissions_other & 1) {
mode |= S_IXOTH;
}

if (0 != chmod(argv[3], mode)) {
printf("chmod error : %s\r\n", strerror(errno));
} else {
printf("chmod ok\r\n");
}

return TRUE;
}

/**
shell@armani:/data/local/tmp $ ./hw_cmd ls file
argc = 3
argv[0] = ./hw_cmd
argv[1] = ls
argv[2] = file
*/
void fn_parse_cmd(int argc, char** argv) {
int i = 0;

printf("%s\r\n", LINE);
printf("argc = %d ", argc);
for (i = 0; i < argc; i++) {
printf("argv[%d] = %s ", i, argv[i]);
}
printf("\r\n%s\r\n", LINE);
}

void fn_help() {
printf("%s\r\n", LINE);
printf("usage:\r\n");

printf("%s\r\n", LINE);
printf("ls <dirpathname>\r\n");
printf("ls <dir>\r\n");
printf("\t display the files attrib on the dir\r\n");

printf("%s\r\n", LINE);
printf("ls <filepathname>\r\n");
printf("ls <file>\r\n");
printf("\t display the file attrib\r\n");

printf("%s\r\n", LINE);
printf("chmod nnn <filename>\r\n");
printf("chmod nnn <dirname>\r\n");
printf("ls <file>\r\n");
printf("\t change the file or dir attrib\r\n");
printf("\t n is digital from 0 ~ 7\r\n");

printf("%s\r\n", LINE);
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: