文件锁

文件锁仅在不同进程间访问起作用。
通过锁同步多个进程对同一个文件的读写访问。
#include<stdio.h>
#include<unistd.h>
#include<fcntl.h>
#include<string.h>
#include<sys/types.h>
#include<stdlib.h>

#define LEN 1000

void menu(){
	printf("------------------------\n");
	printf("********菜单**********\n");
	printf("********1.写	******\n");
	printf("********2.读	******\n");
	printf("********3.测试能否上锁\n");
	printf("********4.上读锁		**\n");
	printf("********5.上写锁		**\n");
	printf("********6.解锁		**\n");
	printf("********7.退出		**\n");
}

void plock(struct flock lock){
	if(lock.l_type == F_UNLCK){
		printf("能上锁\n");
	}else{
		printf("%d进程,",lock.l_pid);
		switch(lock.l_whence){
			case SEEK_SET:
				printf("在距离文件头");
				break;
			case SEEK_CUR:
				printf("在距离当前位置");
				break;
			case SEEK_END:
				printf("在距离文件末尾位置");
				break;
		}
		printf("偏移%ld,长度为%ld",lock.l_start,lock.l_len);
		switch(lock.l_type ){
			case  F_RDLCK:
				printf("为读锁\n");
				break;
			case  F_WRLCK:
				printf("为写锁\n");
				break;
		}
	}
}

int  wtest(int fd,off_t start,off_t len){		//写锁
	struct flock lock={};
	lock.l_type = F_WRLCK;
	lock.l_whence = SEEK_SET;
	lock.l_start = start;
	lock.l_len = len;
	lock.l_pid  =-1;
	if(fcntl(fd,F_GETLK,&lock) == -1){
	//	printf("不能上写锁");
		return -1;
	}
	plock(lock);
	return 0;
}



int  rtest(int fd,off_t start,off_t len){		//读锁
	struct flock lock={};

	lock.l_type = F_RDLCK;
	lock.l_whence = SEEK_SET;
	lock.l_start = start;
	lock.l_len = len;
	lock.l_pid  =-1;

	if(fcntl(fd,F_GETLK,&lock) == -1){
	//	printf("不能上读锁");
		return -1;
	}
	plock(lock);
	return 0;
}

int w_lock(int fd,off_t start,off_t len){
	 struct flock lock = {};

	 lock.l_type = F_WRLCK;
	 lock.l_whence = SEEK_SET;
	 lock.l_start = start;
	 lock.l_len = len;
	 lock.l_pid = -1;
	 printf("0.上阻塞的锁\n");
	 printf("1.上非阻塞的锁\n");
	 int wait = 0;
	 scanf("%d",&wait);
	return fcntl(fd,wait?F_SETLK:F_SETLKW,&lock);
}
int r_lock(int fd,off_t start,off_t len){
	 struct flock lock = {};
	 lock.l_type = F_RDLCK;
	 lock.l_whence = SEEK_SET;
	 lock.l_start = start;
	 lock.l_len = len;
	 lock.l_pid = -1;
	 printf("0.上阻塞的锁\n");
	 printf("1.上非阻塞的锁\n");
	 int wait = 0;
	 scanf("%d",&wait);
	return fcntl(fd,wait?F_SETLK:F_SETLKW,&lock);
}

int un_lock(int fd,off_t start,off_t len){

	struct flock lock;
	lock.l_type = F_UNLCK;
	lock.l_whence = SEEK_SET;
	lock.l_start = start;
	lock.l_len = len;
	lock.l_pid = -1;
	return fcntl(fd,F_SETLK,&lock);
}

void test(const char *filename){
	int fd = open(filename,O_CREAT|O_RDWR,0644);
	if(fd == -1){
		perror("open:");
		return;
	}
	while(1){
		menu();
		int opt = 0;
		printf("请输入选择:\n");
		scanf("%d",&opt);
		switch(opt){
			case 1:{
				char str[LEN]={};
				printf("请输入要写入文件的数据:\n");
				scanf("%s",str);
				lseek(fd,0,SEEK_END);
				int res = write(fd,str,strlen(str));
				if(res == -1){
					perror("write:");	
					return;
				}
			}
				break;
			case 2:{
				char mid[LEN];
				lseek(fd,0,SEEK_SET);
				while(read(fd,mid,LEN)>0){
					printf("%s",mid);
				}
				printf("\n");
			}
			break;
			case 3:{
				printf(">>>>>\n");
				printf("*****1.能否上读锁*****\n");
				printf("*****2.能否上写锁*****\n");
				printf("请输入选择:\n");
				int opt = 0;
				scanf("%d",&opt);
				printf("请输入上锁的偏移距离:\n");
				off_t start = 0;
				scanf("%ld",&start);
				printf("请输入上锁的长度:\n");
				off_t len = 0;
				scanf("%ld",&len);
				if(opt == 1){
					rtest(fd,start,len);
				}else{
					wtest(fd,start,len);
				}
			}
				break;
			case 4:{
				printf("请输入上锁的偏移距离:\n");
				off_t start = 0;
				scanf("%ld",&start);
				printf("请输入上锁的长度:\n");
				off_t len = 0;
				scanf("%ld",&len);
				if(r_lock(fd,start,len)==-1){
					printf("上锁失败\n");
				}else{
					printf("上锁成功\n");
				}
			}
				break;
			case 5:{
				printf("请输入上锁的偏移距离:\n");
				off_t start = 0;
				scanf("%ld",&start);
				printf("q请输入上锁的长度:\n");
				off_t len = 0;
				scanf("%ld",&len);
				if(w_lock(fd,start,len)==-1){
					printf("上锁失败\n");
				}else{
					printf("上锁成功\n");
				}
			}
				break;
			case 6:{
				printf("请输入解锁的偏移距离:\n");
				off_t start = 0;
				scanf("%ld",&start);
				printf("q请输入解锁的长度:\n");
				off_t len = 0;
				scanf("%ld",&len);
				if(un_lock(fd,start,len)==-1){
					printf("解锁失败\n");
				}else{
					printf("解锁成功\n");
				}
			}
				break;
			case 7:
				exit(0);
		}
	}
	close(fd);
}



int main(int argc,char *argv[]){
	if(argc<2){
		printf("%d is not enough!\n",argc);
		return -1;
	}

	test(argv[1]);
	return 0;

}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值