linux 调用系统函数来实现 ATM 自动取款机功能 (进程间通信)
ATM取款机功能包含7个操作:
(1)开户
(2)销户
(3)存款
(4)取款
(5)查询
(6)转账
(7)退出
然后定义客户端和服务器端 进行在linux操作系统下 进程间的通信
注: 在linux控制台下按一下顺序链接
server:
gcc server.c bank.c -o server
client:
gcc client.c bank.c -o client
open:
gcc open.c bank.c dao.c -o open
然后先运行./server
再运行./client
client.c
1 /* 客户端*/ 2 #include <stdio.h> 3 #include "bank.h" 4 #include <sys/types.h> 5 #include <sys/ipc.h> 6 #include <sys/msg.h> 7 #include <stdlib.h> 8 #include <string.h> 9 10 static int msgid1;//定义两个接受消息队列的id的变量 11 static int msgid2; 12 //获取消息队列函数, 13 void getID(){ 14 msgid1 = msgget(key1,0); 15 if(msgid1 == -1){ 16 perror("获取消息队列1失败"); 17 exit(-1); 18 } 19 msgid2 = msgget(key2,0); 20 if(msgid2 == -1){ 21 perror("获取消息队列2失败"); 22 exit(-1); 23 } 24 } 25 //开户函数 26 void createUser(){ 27 struct Account acc; 28 printf("请输入用户名:\n"); 29 scanf("%s",acc.name); 30 printf("请输入密码:\n"); 31 scanf("%s",acc.password); 32 printf("请输入金额:\n"); 33 scanf("%lf",&acc.balance); 34 struct Msg msg = {M_OPEN,acc}; 35 //获取消息队列 36 getID(); 37 //将消息发送到消息队列1中 38 msgsnd(msgid1,&msg,sizeof(msg.acc),0); 39 //接受消息队列2中的消息 40 msgrcv(msgid2,&msg,sizeof(msg.acc),0,0); 41 if(msg.mtype == M_SUCCESS){ 42 printf("开户成功!\n"); 43 printf("Your ID is : %d\n",msg.acc.id); 44 printf("Your name is : %s\n",msg.acc.name); 45 printf("Your deposit is : %.2lf RMB\n",msg.acc.balance); 46 } 47 else{ 48 printf("开户失败!\n"); 49 } 50 } 51 //销户 52 void destroyUser(){ 53 struct Account acc; 54 printf("请输入销毁账户的ID号(注账户有余额时不能销毁):"); 55 scanf("%d",&acc.id); 56 printf("请输入销毁账户的密码:"); 57 scanf("%s",acc.password); 58 struct Msg msg = {M_DESTROY,acc}; 59 getID(); 60 msgsnd(msgid1,&msg,sizeof(msg.acc),0); 61 msgrcv(msgid2,&msg,sizeof(msg.acc),0,0); 62 if(msg.mtype == M_SUCCESS){ 63 printf("销毁账户成功\n"); 64 } 65 else{ 66 printf("销毁账户失败\n"); 67 printf("您的账户ID和密码输入错误或您的账户存在余额\n"); 68 } 69 } 70 //存钱 71 void saveMoney(){ 72 struct Account acc; 73 printf("请输入存款账户的ID号:"); 74 scanf("%d",&acc.id); 75 printf("请输入存款账户的密码:"); 76 scanf("%s",acc.password); 77 printf("请输入存款金额:"); 78 scanf("%lf",&acc.balance); 79 struct Msg msg = {M_SAVE,acc}; 80 getID(); 81 msgsnd(msgid1,&msg,sizeof(msg.acc),0); 82 msgrcv(msgid2,&msg,sizeof(msg.acc),0,0); 83 if(msg.mtype == M_SUCCESS){ 84 printf("存款成功\n"); 85 printf("Your ID is : %d\n",msg.acc.id); 86 printf("Your name is : %s\n",msg.acc.name); 87 printf("Your deposit is : %.2lf RMB\n",msg.acc.balance); 88 } 89 else{ 90 printf("存款失败\n"); 91 printf("账户ID或密码错误\n"); 92 } 93 } 94 //取钱 95 void getMoney(){ 96 struct Account acc; 97 printf("请输入取款账户的ID号:"); 98 scanf("%d",&acc.id); 99 printf("请输入取款账户的密码:"); 100 scanf("%s",acc.password); 101 printf("请输入要取款的金额:"); 102 scanf("%lf",&acc.balance); 103 struct Msg msg = {M_TAKE,acc}; 104 getID(); 105 msgsnd(msgid1,&msg,sizeof(msg.acc),0); 106 msgrcv(msgid2,&msg,sizeof(msg.acc),0,0); 107 if(msg.mtype == M_SUCCESS){ 108 printf("取款成功\n"); 109 printf("Your ID is : %d\n",msg.acc.id); 110 printf("Your name is : %s\n",msg.acc.name); 111 printf("Your deposit is : %.2lf RMB\n",msg.acc.balance); 112 } 113 else{ 114 printf("取款失败\n"); 115 printf("账户ID和密码输入错误 或 取款金额大于银行账户金额\n"); 116 } 117 } 118 //查询 119 void checkMoney(){ 120 struct Account acc; 121 printf("请输入您账户的ID号:"); 122 scanf("%d",&acc.id); 123 printf("请输入您账户的密码:"); 124 scanf("%s",acc.password); 125 struct Msg msg = {M_QUERY,acc}; 126 getID(); 127 msgsnd(msgid1,&msg,sizeof(msg.acc),0); 128 msgrcv(msgid2,&msg,sizeof(msg.acc),0,0); 129 if(msg.mtype == M_SUCCESS){ 130 printf("查询操作成功\n"); 131 printf("您银行卡ID号为:%d\n",msg.acc.id); 132 printf("您的用户名是:%s\n",msg.acc.name); 133 printf("您账户中所剩的余额是:%.2lf\n",msg.acc.balance); 134 } 135 else{ 136 printf("账户id和密码输入错误\n"); 137 } 138 139 } 140 //转账 141 void moveMoney(){ 142 struct Account acc; 143 printf("请输入您账号的ID号:"); 144 scanf("%d",&acc.id); 145 printf("请输入您账户的密码:"); 146 scanf("%s",acc.password); 147 struct Msg msg = {M_TRANSF,acc}; 148 msgsnd(msgid1,&msg,sizeof(msg.acc),0); 149 printf("请输入要转入账户的ID:"); 150 scanf("%d",&acc.id); 151 printf("请输入你要转入账号的金额:"); 152 scanf("%lf",&acc.balance); 153 msg.acc = acc; 154 msgsnd(msgid1,&msg,sizeof(msg.acc),0); 155 msgrcv(msgid2,&msg,sizeof(msg.acc),0,0); 156 if(msg.mtype == M_SUCCESS){ 157 printf("转账成功\n"); 158 printf("Your ID is : %d\n",msg.acc.id); 159 printf("Your name is : %s\n",msg.acc.name); 160 printf("Your deposit is : %.2lf RMB\n",msg.acc.balance); 161 } 162 else{ 163 printf("转账失败,请重试\n"); 164 } 165 } 166 167 //客户端界面 168 void mainPage(){ 169 while(1){ 170 printf(" 欢迎使用迷你ATM机\n"); 171 printf("---------------------\n"); 172 printf("[1] 开户"); 173 printf(" [2] 销户\n"); 174 printf("[3] 存钱"); 175 printf(" [4] 取钱\n"); 176 printf("[5] 查询"); 177 printf(" [6] 转账\n"); 178 printf("[0] 退出\n"); 179 printf("---------------------\n"); 180 printf("请选择:\n"); 181 int num = 0; 182 scanf("%d",&num); 183 switch(num){ 184 case 1:createUser();break; 185 case 2:destroyUser();break; 186 case 3:saveMoney();break; 187 case 4:getMoney();break; 188 case 5:checkMoney();break; 189 case 6:moveMoney();break; 190 case 0:printf("谢谢使用,再见!\n");return ; 191 default:printf("输入错误\n"); 192 } 193 } 194 } 195 int main(){ 196 mainPage(); 197 return 0; 198 }
bank.c
1 //对头文件中的变量进行定义 2 #include "bank.h" 3 struct Msg msgResult ={}; 4 const int key1 = 0x12345678; 5 const int key2 = 0x23456789;
dao.c
1 #include "dao.h" 2 #include <unistd.h> 3 #include <stdio.h> 4 #include <sys/types.h> 5 #include <fcntl.h> 6 #include <stdlib.h> 7 #include <string.h> 8 //定义一个文件来存储帐号 9 const char* ID_FILE = "./dataBase/id.dat"; 10 static int x = 100000; 11 int moneyTransf(struct Account acc,struct Account accResult){ 12 struct Account accMove; 13 char filename[40]={"./dataBase/"}; 14 sprintf(filename,"./dataBase/%d.dat",acc.id);//为每个帐号建立一个文件 15 if(access(filename,F_OK) == -1){ //是否存在这个文件 16 printf("文件不存在\n"); 17 return -1; 18 } 19 int fd = open(filename,O_RDWR,0600); 20 if(fd == -1){ 21 perror("查询失败"); 22 return -1; 23 } 24 if(read(fd,&accMove,sizeof(accMove)) < 0){ 25 return -1; 26 } 27 if(accMove.balance < accResult.balance){ 28 return -1; 29 } 30 if(accMove.id == acc.id && strcmp(accMove.password,acc.password) == 0){ 31 msgResult.acc.id = accMove.id; 32 strcpy(msgResult.acc.password,acc.password); 33 strcpy(msgResult.acc.name,accMove.name); 34 msgResult.acc.balance = accMove.balance - accResult.balance; 35 }else{ 36 perror("账户ID和密码不匹配"); 37 return -1; 38 } 39 sprintf(filename,"./dataBase/%d.dat",accResult.id);//为每个帐号建立一个文件 40 if(access(filename,F_OK) == -1){ //是否存在这个文件 41 printf("文件不存在\n"); 42 return -1; 43 } 44 int fp = open(filename,O_RDWR,0600); 45 if(fp == -1){ 46 perror("查询失败"); 47 return -1; 48 } 49 if(read(fp,&accMove,sizeof(accMove)) < 0){ 50 return -1; 51 } 52 if(accMove.id == accResult.id){ 53 accMove.balance += accResult.balance; 54 lseek(fp,0,SEEK_SET); 55 write(fp,&accMove,sizeof(accMove)); 56 lseek(fd,0,SEEK_SET); 57 write(fd,&msgResult.acc,sizeof(msgResult.acc)); 58 }else{ 59 perror("账户ID和密码不匹配"); 60 return -1; 61 } 62 63 close(fd); 64 close(fp); 65 //printf("创建用户成功\n"); 66 return 0; 67 68 } 69 70 int Query(struct Account acc){ 71 struct Account accMove; 72 char filename[40]={"./dataBase/"}; 73 sprintf(filename,"./dataBase/%d.dat",acc.id);//为每个帐号建立一个文件 74 if(access(filename,F_OK) == -1){ //是否存在这个文件 75 printf("文件不存在\n"); 76 return -1; 77 } 78 int fd = open(filename,O_RDWR,0600); 79 if(fd == -1){ 80 perror("查询失败"); 81 return -1; 82 } 83 if(read(fd,&accMove,sizeof(accMove)) < 0){ 84 return -1; 85 } 86 if(accMove.id == acc.id && strcmp(accMove.password,acc.password) == 0){ 87 msgResult.acc.id = accMove.id; 88 strcpy(msgResult.acc.name,accMove.name); 89 msgResult.acc.balance = accMove.balance; 90 }else{ 91 perror("账户ID和密码不匹配"); 92 return -1; 93 } 94 close(fd); 95 //printf("创建用户成功\n"); 96 return 0; 97 98 } 99 int takeMoney(struct Account acc){ //取款操作 100 struct Account accMove; 101 char filename[40]={"./dataBase/"}; 102 sprintf(filename,"./dataBase/%d.dat",acc.id);//为每个帐号建立一个文件 103 if(access(filename,F_OK) == -1){ //是否存在这个文件 104 printf("文件不存在\n"); 105 return -1; 106 } 107 int fd = open(filename,O_RDWR,0600); 108 if(fd == -1){ 109 perror("取款失败"); 110 return -1; 111 } 112 if(read(fd,&accMove,sizeof(accMove)) < 0){ 113 return -1; 114 } 115 if(accMove.id == acc.id && strcmp(accMove.password,acc.password) == 0){ 116 if(accMove.balance-acc.balance < -0.01){ 117 printf("所取余额大于存款金额\n"); 118 return -1; 119 } 120 accMove.balance -= acc.balance; 121 lseek(fd,0,SEEK_SET); 122 write(fd,&accMove,sizeof(accMove)); 123 msgResult.acc.id = accMove.id; 124 strcmp(msgResult.acc.name,accMove.name); 125 msgResult.acc.balance = accMove.balance; 126 }else{ 127 perror("账户ID和密码不匹配"); 128 return -1; 129 } 130 close(fd); 131 //printf("创建用户成功\n"); 132 return 0; 133 } 134 int putMoney(struct Account acc){ //存款操作 135 struct Account accMove; 136 char filename[20]={"./dataBase/"}; 137 sprintf(filename,"./dataBase/%d.dat",acc.id);//为每个帐号建立一个文件 138 if(access(filename,F_OK) == -1){ //是否存在这个文件 139 printf("文件不存在\n"); 140 return -1; 141 } 142 int fd = open(filename,O_RDWR,0600); 143 if(fd == -1){ 144 perror("存款失败"); 145 return -1; 146 } 147 if(read(fd,&accMove,sizeof(accMove)) < 0){ 148 return -1; 149 } 150 if(accMove.id == acc.id && strcmp(accMove.password,acc.password) == 0){ 151 accMove.balance += acc.balance; 152 lseek(fd,0,SEEK_SET); 153 write(fd,&accMove,sizeof(accMove)); 154 msgResult.acc.id = accMove.id; 155 strcmp(msgResult.acc.name,accMove.name); 156 msgResult.acc.balance = accMove.balance; 157 }else{ 158 perror("账户ID和密码不匹配"); 159 return -1; 160 } 161 close(fd); 162 //printf("创建用户成功\n"); 163 return 0; 164 } 165 166 167 168 int destroyUser(struct Account acc){ //删除账户操作 169 struct Account accMove; 170 char filename[40]={"./dataBase/"}; 171 sprintf(filename,"./dataBase/%d.dat",acc.id);//为每个帐号建立一个文件 172 if(access(filename,F_OK) == -1){ //是否存在这个文件 173 return -1; 174 } 175 int fd = open(filename,O_RDWR,0600); 176 if(fd == -1){ // 读取文件失败 177 perror("删除帐户文件失败"); 178 return -1; 179 } 180 if(read(fd,&accMove,sizeof(accMove)) < 0){ //读取账户内容失败 181 return -1; 182 } 183 if(accMove.balance > 0.01){ //账户存在余额,无法销户 184 perror("账户存在余额,无法销户"); 185 return -1; 186 } 187 if(accMove.id == acc.id && strcmp(accMove.password,acc.password) == 0){ 188 remove(filename); 189 }else{ 190 perror("账户ID和密码不匹配"); 191 return -1; 192 } 193 194 close(fd); 195 //printf("创建用户成功\n"); 196 return 0; 197 } 198 199 int get_id(){ //获得ID号 200 if(access(ID_FILE,F_OK)){ 201 int fd = open(ID_FILE,O_WRONLY|O_CREAT|O_EXCL,0600); 202 if(fd == -1){ 203 perror("文件打开失败"); 204 return -1; 205 } 206 write(fd,&x,sizeof(x));//写入文件 207 close(fd); 208 return x; 209 } 210 int fd = open(ID_FILE,O_RDWR); 211 if(fd == -1){ 212 perror("文件打开失败"); 213 return -1; 214 } 215 read(fd,&x,sizeof(x)); 216 return x; 217 } 218 219 //生成不重复的帐号 220 int generator_id(){ 221 if(access(ID_FILE,F_OK)){//判断文件是否存在,不存在返回-1 222 //不存在就创建 223 int fd = open(ID_FILE,O_WRONLY|O_CREAT|O_EXCL,0600); 224 if(fd == -1){ 225 perror("文件打开失败"); 226 return -1; 227 } 228 write(fd,&x,sizeof(x));//写入文件 229 close(fd); 230 return x; 231 } 232 //如果文件存 233 int fd = open(ID_FILE,O_RDWR); 234 if(fd == -1){ 235 perror("文件打开失败"); 236 return -1; 237 } 238 //将文件中的数值读到x中 239 read(fd,&x,sizeof(x)); 240 x++;//保证帐号唯一 241 //将读写位置置到文件开始头 242 lseek(fd,0,SEEK_SET); 243 //再将x的值写到文件中,覆盖原来的x 244 write(fd,&x,sizeof(x)); 245 close(fd); 246 return x; 247 } 248 249 250 251 252 //将一个新帐号 存到文件中 253 int createUser(struct Account acc){ 254 char filename[40]={"./dataBase/"}; 255 sprintf(filename,"./dataBase/%d.dat",acc.id);//为每个帐号建立一个文件 256 int fd = open(filename,O_WRONLY|O_CREAT|O_EXCL,0600); 257 if(fd == -1){ 258 perror("创建帐户文件失败"); 259 return -1; 260 } 261 if(write(fd,&acc,sizeof(acc)) < 0){ 262 return -1; 263 } 264 close(fd); 265 msgResult.acc.id = acc.id; 266 strcpy(msgResult.acc.name,acc.name); 267 msgResult.acc.balance = acc.balance; 268 //printf("创建用户成功\n"); 269 return 0; 270 }
open.c
1 /*开户*/ 2 #include <stdio.h> 3 #include <stdlib.h> 4 #include <sys/types.h> 5 #include <sys/ipc.h> 6 #include <sys/msg.h> 7 #include "bank.h" 8 #include "dao.h" 9 int main(){ 10 int msgid1 = msgget(key1,0); 11 if(msgid1 == -1){ 12 perror("获取消息队列1失败"); 13 printf("服务器启动失败"); 14 exit(-1); 15 } 16 int msgid2 = msgget(key2,0); 17 if(msgid2 == -1){ 18 perror("获取消息队列2失败"); 19 printf("服务器启动失败"); 20 exit(-1); 21 } 22 //获取到消息队列之后,开始接受消息 23 while(1){ 24 struct Msg msg;//存储消息信息的结构体 25 struct Account accMove,accResult;//存储帐户信息 26 //首先从客户那里收取消息队列1的信息 msgrcv 函数 27 if(msgrcv(msgid1,&msg,sizeof(msg.acc),0,0) <=0 ){ 28 break; 29 } 30 //如果接受到了消息,根据消息的不同类型进行不同的操作 31 if(msg.mtype == M_OPEN){//如果类型是开户 32 int id = generator_id(); 33 accMove = msg.acc; 34 accMove.id = id; 35 if(createUser(accMove)==-1){ 36 printf("开户失败"); 37 msgResult.mtype = M_FAILED;//将消息类型置成失败 38 } 39 else{ 40 printf("开户成功"); 41 msgResult.mtype = M_SUCCESS; 42 } 43 msgsnd(msgid2,&msgResult,sizeof(msgResult.acc),0);//将消息由消息队列2发送给客户端 44 //执行开户的操作 45 //给用户分配帐号,将用户信息记录在文件中。 46 } 47 //最后把消息发过去,这时候消息的类型应该是两种情况M_SUCESS 48 //或者是M_FAILED 49 else if(msg.mtype == M_DESTROY){ 50 accMove = msg.acc; 51 if(destroyUser(accMove)==-1){ 52 printf("销户失败"); 53 msgResult.mtype = M_FAILED;//将消息类型置成失败 54 } 55 else{ 56 printf("销户成功"); 57 msgResult.mtype = M_SUCCESS; 58 } 59 msgsnd(msgid2,&msgResult,sizeof(msgResult.acc),0);//将消息由消息队列2发送给客户端 60 } 61 else if(msg.mtype == M_SAVE){ 62 accMove = msg.acc; 63 if(putMoney(accMove)==-1){ 64 printf("存款失败"); 65 msgResult.mtype = M_FAILED;//将消息类型置成失败 66 } 67 else{ 68 printf("存款成功"); 69 msgResult.mtype = M_SUCCESS; 70 } 71 msgsnd(msgid2,&msgResult,sizeof(msgResult.acc),0);//将消息由消息队列2发送给客户端 72 } 73 else if(msg.mtype == M_TAKE){ 74 accMove = msg.acc; 75 if(takeMoney(accMove)==-1){ 76 printf("取款失败"); 77 msgResult.mtype = M_FAILED;//将消息类型置成失败 78 } 79 else{ 80 printf("取款成功"); 81 msgResult.mtype = M_SUCCESS; 82 } 83 msgsnd(msgid2,&msgResult,sizeof(msgResult.acc),0);//将消息由消息队列2发送给客户端 84 } 85 else if(msg.mtype == M_QUERY){ 86 accMove = msg.acc; 87 if(Query(accMove)==-1){ 88 printf("查询失败"); 89 msgResult.mtype = M_FAILED;//将消息类型置成失败 90 } 91 else{ 92 printf("查询成功"); 93 msgResult.mtype = M_SUCCESS; 94 } 95 msgsnd(msgid2,&msgResult,sizeof(msgResult.acc),0);//将消息由消息队列2发送给客户端 96 } 97 else if(msg.mtype == M_TRANSF){ 98 accMove = msg.acc; 99 if(msgrcv(msgid1,&msg,sizeof(msg.acc),0,0) <=0 ){ 100 msgResult.mtype = M_FAILED; 101 } 102 else { 103 accResult = msg.acc; 104 if(moneyTransf(accMove,accResult)==-1){ 105 printf("转账失败"); 106 msgResult.mtype = M_FAILED;//将消息类型置成失败 107 } 108 else{ 109 printf("转账成功"); 110 msgResult.mtype = M_SUCCESS; 111 } 112 } 113 msgsnd(msgid2,&msgResult,sizeof(msgResult.acc),0);//将消息由消息队列2发送给客户端 114 } 115 116 } 117 return 0; 118 }
server.c
1 //ATM的服务器端 2 #include "bank.h" 3 #include <sys/types.h> 4 #include <sys/ipc.h> 5 #include <sys/msg.h> 6 #include <stdio.h> 7 #include <stdlib.h> 8 #include <unistd.h> 9 #include <signal.h> 10 11 //首先需要创建两个全局存储消息队列的id的变量 12 static int msgid1; 13 static int msgid2; 14 //写一个函数,用来创建两个消息队列,用到msgget函数 15 void init(){ 16 //msgget函数,第一个参数是键值,bank.h中有 17 //IPC_CREAT表示没有此消息队列则创建, 18 //IPC_EXCL表示如果队列存在,则提示错误 19 //0666是给此消息队列对象添加一些权限设置,类似文件系统 20 //创建消息队列1 21 msgid1 = msgget(key1,IPC_CREAT|IPC_EXCL|0666); 22 if(msgid1 == -1){ 23 perror("消息队列1创建失败"),exit(-1); 24 } 25 printf("消息队列1创建成功\n"); 26 //创建消息队列2 27 msgid2 = msgget(key2,IPC_CREAT|IPC_EXCL|0666); 28 if(msgid2 == -1){ 29 perror("消息队列2创建失败"); 30 exit(-1); 31 } 32 printf("消息队列2创建成功\n"); 33 } 34 //启动服务函数,用来创建子进程来执行用户不同的选择的结果 35 void start(){ 36 printf("服务器正在启动..\n"); 37 sleep(2); 38 //创建子进程 39 pid_t open_pid = vfork(); 40 if(open_pid == -1){ 41 perror("vfork failed"); 42 exit(-1); 43 } 44 else if(open_pid == 0){//进入子进程 45 //printf("in child process\n"); 46 execl("open","open",NULL);//不再和父进程共用代码段 47 } 48 else{ 49 printf("正在等待客户端选择..\n"); 50 waitpid(open_pid,0,0);//阻塞,等待子进程结束 51 //printf("in parent process\n"); 52 } 53 } 54 55 void sig_exit(int signo){ 56 printf("服务器正在关闭..\n"); 57 sleep(2); 58 if(msgctl(msgid1,IPC_RMID,NULL) == -1){ 59 perror("消息队列1删除失败\n"); 60 exit(-1); 61 } 62 else{ 63 printf("消息队列1删除成功\n"); 64 } 65 if(msgctl(msgid2,IPC_RMID,NULL) == -1){ 66 perror("消息队列2删除失败\n"); 67 exit(-1); 68 } 69 else{ 70 printf("消息队列2删除成功\n"); 71 } 72 printf("服务器成功关闭\n"); 73 exit(0);//直接结束程序 74 75 } 76 int main(){ 77 //我们退出服务器用一个信号处理函数来实现 78 printf("退出服务器请按CTRL+C\n");//发送SIGINT信号 79 signal(SIGINT,sig_exit);//自定义信号处理函数,进行退出操作 80 //做好了善后工作,我们从头开始启动服务器 81 //创建消息队列 82 init(); 83 //启动服务 84 85 start(); 86 return 0; 87 }
bank.h
1 //客户端和服务器端共用的头文件 2 #ifndef BANK_H_ 3 #define BANK_H_ 4 //声明两个key值,用来给消息队列用,这两个key在另一个文件中定义 5 6 extern const int key1;//客户端向服务器发送消息队列的键值key 7 extern const int key2;//服务器向客户端发送的 8 9 //消息类型 定义为各种宏 方便处理 10 #define M_OPEN 1//代表开户类型 11 #define M_DESTROY 2 //销户 12 #define M_SAVE 3 //存钱 13 #define M_TAKE 4 //取钱 14 #define M_QUERY 5 //查询 15 #define M_TRANSF 6 //转账 16 #define M_SUCCESS 7 //处理成功 17 #define M_FAILED 8 //处理失败 18 19 //包含帐户信息的帐户结构体 20 struct Account{ 21 int id;//帐号 22 char name[10];//用户名 23 char password[10];//密码 24 double balance;//金额 25 }; 26 27 //消息的结构体 28 struct Msg{ 29 long mtype;//消息的类型 30 struct Account acc;//帐户的信息结构体 31 }; 32 extern struct Msg msgResult; 33 #endif
dao.h
1 //数据对象的存储 2 #ifndef DAO_H_ 3 #define DAO_H_ 4 #include "bank.h" 5 //生成不重复的帐号 6 int generator_id(); 7 //将新帐号添加到文件中,为开户服务 8 int createUser(struct Account acc); 9 //销户功能 10 int destroyUser(struct Account acc); 11 //存钱功能 12 int saveMoney(struct Account acc,struct Account *p); 13 //取钱功能 14 int getMoney(struct Account acc,struct Account *p); 15 //查询余额功能 16 int checkMoney(struct Account acc,struct Account *p); 17 //转账功能 18 int moveMoney(struct Account acc1,struct Account acc2,struct Account *p); 19 #endif