linux用户编程技巧

上传人:仙*** 文档编号:183373659 上传时间:2023-01-30 格式:DOC 页数:11 大小:58KB
收藏 版权申诉 举报 下载
linux用户编程技巧_第1页
第1页 / 共11页
linux用户编程技巧_第2页
第2页 / 共11页
linux用户编程技巧_第3页
第3页 / 共11页
资源描述:

《linux用户编程技巧》由会员分享,可在线阅读,更多相关《linux用户编程技巧(11页珍藏版)》请在装配图网上搜索。

1、1、 当找不到某个函数的库名称时,怎么办?例:sin函数,使用 nm o /lib/*.so|grep sin/sin 命令2、 得到进程IDgetpid,得到父进程IDgetppid#include pid_t getpid(void); pid_t getppid(void);得到进程所有者IDgetuid,得到进程有效用户IDgeteuid,得到进程所在组IDgetgid,得到有效组IDgetegid#include#includeuid_t getuid(void); uid_t geteuid(void); uid_t getgid(void); uid_t getegid(void

2、);得到用户的其他信息structpasswdchar*pw_name;/*登录名称*/ char*pw_passwd;/*登录口令*/ uid_tpw_uid;/*用户ID*/ gid_tpw_gid;/*用户组ID*/ char*pw_gecos;/*用户的真名*/ char*pw_dir;/*用户的目录*/ char*pw_shell;/*用户的SHELL*/;#include#includestructpasswd*getpwuid(uid_tuid);3、 创建进程#includepid_tfork();4、 子进程继续执行,而父进程阻塞直到子进程完成任务.#include#incl

3、udepid_twait(int*stat_loc);pid_twaitpid(pid_tpid,int*stat_loc,intoptions);stat_loc是子进程的退出状态.子进程调用exit,_exit或者是return来设置这个值.为了得到这个值Linux定义了几个宏来测试这个返回值.WIFEXITED:判断子进程退出值是非0WEXITSTATUS:判断子进程的退出值(当子进程退出时非0).WIFSIGNALED:子进程由于有没有获得的信号而退出.WTERMSIG:子进程没有获得的信号号(在WIFSIGNALED为真时才有意义).waitpid等待指定的子进程直到子进程返回.如果

4、pid为正值则等待指定的进程(pid).如果为0则等待任何一个组ID和调用者的组ID相同的进程.为-1时等同于wait调用.小于-1时等待任何一个组ID等于pid绝对值的进程. options可以决定父进程的状态.可以取两个值WNOHANG:父进程立即返回当没有子进程存在时.WUNTACHED:当子进程结束时waitpid返回,但是子进程的退出状态不可得到.为了调用系统程序,我们可以使用系统调用exec族调用.exec族调用有着5个函数.#includeintexecl(constchar*path,constchar*arg,.);intexeclp(constchar*file,const

5、char*arg,.);intexecle(constchar*path,constchar*arg,.);intexecv(constchar*path,char*constargv);intexecvp(constchar*file,char*constargv):5、 在命令后面加上&符号SHELL就会把我们的程序放到后台去运行的.6、 文件操作#include#include#include#includeintopen(constchar*pathname,intflags);intopen(constchar*pathname,intflags,mode_tmode);intclo

6、se(intfd);flags可以去下面的一个值或者是几个值的组合.O_RDONLY:以只读的方式打开文件.O_WRONLY:以只写的方式打开文件.O_RDWR:以读写的方式打开文件.O_APPEND:以追加的方式打开文件.O_CREAT:创建一个文件.O_EXEC:如果使用了O_CREAT而且文件已经存在,就会发生一个错误.O_NOBLOCK:以非阻塞的方式打开一个文件.O_TRUNC:如果文件已经存在,则删除文件的内容.如果使用了O_CREATE标志,那么我们要使用open的第二种形式.还要指定mode标志,用来表示文件的访问权限.mode可以是以下情况的组合.-S_IRUSR用户可以读S

7、_IWUSR用户可以写S_IXUSR用户可以执行S_IRWXU用户可以读写执行-S_IRGRP组可以读S_IWGRP组可以写S_IXGRP组可以执行S_IRWXG组可以读写执行-S_IROTH其他人可以读S_IWOTH其他人可以写S_IXOTH其他人可以执行S_IRWXO其他人可以读写执行-S_ISUID设置用户执行IDS_ISGID设置组的执行ID-#includessize_tread(intfd,void*buffer,size_tcount);ssize_twrite(intfd,constvoid*buffer,size_tcount);如果read读到了文件的结尾或者被一个信号所中

8、断,返回值会小于count.如果是由信号中断引起返回,而且没有返回数据,read会返回-1,且设置errno为EINTR.当程序读到了文件结尾的时候,read会返回0.7、 判断文件是否可以进行某种操作(读,写等等).#includeintaccess(constchar*pathname,intmode);pathname:是文件名称,mode是我们要判断的属性.可以取以下值或者是他们的组合.R_OK文件可以读,W_OK文件可以写,X_OK文件可以执行,F_OK文件存在.当我们测试成功时,函数返回0,否则如果有一个条件不符时,返回-1.如果我们要获得文件的其他属性,我们可以使用函数stat或

9、者fstat.#include#includeintstat(constchar*file_name,structstat*buf);intfstat(intfiledes,structstat*buf);structstatdev_tst_dev;/*设备*/ino_tst_ino;/*节点*/mode_tst_mode;/*模式*/nlink_tst_nlink;/*硬连接*/uid_tst_uid;/*用户ID*/gid_tst_gid;/*组ID*/dev_tst_rdev;/*设备类型*/off_tst_off;/*文件字节数*/unsignedlongst_blksize;/*块大

10、小*/unsignedlongst_blocks;/*块数*/time_tst_atime;/*最后一次访问时间*/time_tst_mtime;/*最后一次修改时间*/time_tst_ctime;/*最后一次改变时间(指属性)*/;stat用来判断没有打开的文件,而fstat用来判断打开的文件.我们使用最多的属性是st_mode.通过着属性我们可以判断给定的文件是一个普通文件还是一个目录,连接等等.可以使用下面几个宏来判断.S_ISLNK(st_mode):是否是一个连接.S_ISREG是否是一个常规文件.S_ISDIR是否是一个目录S_ISCHR是否是一个字符设备.S_ISBLK是否是一

11、个块设备S_ISFIFO是否是一个FIFO文件.S_ISSOCK是否是一个SOCKET文件.8、 获取当前工作路径#includechar*getcwd(char*buffer,size_tsize);9、 目录操作#include#include#include#include#includeintmkdir(constchar*path,mode_tmode);DIR*opendir(constchar*path);structdirent*readdir(DIR*dir);voidrewinddir(DIR*dir);off_ttelldir(DIR*dir);voidseekdir(D

12、IR*dir,off_toff);intclosedir(DIR*dir);structdirentlongd_ino;off_td_off;unsignedshortd_reclen;chard_nameNAME_MAX+1;/*文件名称*/10、 管道文件系统调用pipe可以创建一个管道.#includeintpipe(intfildes2);pipe调用可以创建一个管道(通信缓冲区).当调用成功时,我们可以访问文件描述符fildes0,fildes1.其中fildes0是用来读的文件描述符,而fildes1是用来写的文件描述符.11、 为了实现重定向操作,我们需要调用另外一个函数dup2

13、.#includeintdup2(intoldfd,intnewfd);dup2将用oldfd文件描述符来代替newfd文件描述符,同时关闭newfd文件描述符.也就是说,所有向newfd操作都转到oldfd上面.12、 时间#includetime_ttime(time_t*tloc);char*ctime(consttime_t*clock);时间测量#includeintgettimeofday(structtimeval*tv,structtimezone*tz);struttimevallongtv_sec;/*秒数*/longtv_usec;/*微秒数*/;13、 计时器的使用IT

14、IMER_REAL:减少实际时间.到时的时候发出SIGALRM信号.ITIMER_VIRTUAL:减少有效时间(进程执行的时间).产生SIGVTALRM信号.ITIMER_PROF:减少进程的有效时间和系统时间(为进程调度用的时间). 和上面一个使用用来计算系统内核时间和用户时间.产生SIGPROF信号.具体的操作函数是:#includeintgetitimer(intwhich,structitimerval*value);intsetitimer(intwhich,structitimerval*newval,structitimerval*oldval);structitimervals

15、tructtimevalit_interval;structtimevalit_value; getitimer函数得到间隔计时器的时间值.保存在value中setitimer函数设置间隔计时器的时间值为newval.并将旧值保存在oldval中.which表示使用三个计时器中的哪一个.itimerval结构中的it_value是减少的时间,当这个值为0的时候就发出相应的信号了.14、 信号量POSIX的无名信号量的函数有以下几个:#includeintsem_init(sem_t*sem,intpshared,unsignedintvalue);intsem_destroy(sem_t*se

16、m);intsem_wait(sem_t*sem);intsem_trywait(sem_t*sem);intsem_post(sem_t*sem);intsem_getvalue(sem_t*sem);sem_init创建一个信号灯,并初始化其值为value.pshared决定了信号量能否在几个进程间共享.由于目前Linux还没有实现进程间共享信号灯,所以这个值只能够取0.sem_destroy是用来删除信号灯的.sem_wait调用将阻塞进程,直到信号灯的值大于0.这个函数返回的时候自动的将信号灯的值的减一.sem_post和sem_wait相反,是将信号灯的内容加一同时发出信号唤醒等待的

17、进程.sem_trywait和sem_wait相同,不过不阻塞的,当信号灯的值为0的时候返回EAGAIN,表示以后重试.sem_getvalue得到信号灯的值.15、 SystemV信号量 SystemV信号量的函数主要有下面几个.#include#include#includekey_tftok(char*pathname,charproj);intsemget(key_tkey,intnsems,intsemflg);intsemctl(intsemid,intsemnum,intcmd,unionsemunarg);intsemop(intsemid,structsembuf*spos,

18、intnspos);structsembufshortsem_num;/*使用那一个信号*/shortsem_op;/*进行什么操作*/shortsem_flg;/*操作的标志*/;ftok函数是根据pathname和proj来创建一个关键字.semget创建一个信号量.成功时返回信号的ID,key是一个关键字,可以是用ftok创建的也可以是IPC_PRIVATE表明由系统选用一个关键字.nsems表明我们创建的信号个数.semflg是创建的权限标志,和我们创建一个文件的标志相同.semctl对信号量进行一系列的控制.semid是要操作的信号标志,semnum是信号的个数,cmd是操作的命令.

19、经常用的两个值是:SETVAL(设置信号量的值)和IPC_RMID(删除信号灯).arg是一个给cmd的参数.semop是对信号进行操作的函数.semid是信号标志,spos是一个操作数组表明要进行什么操作,nspos表明数组的个数.如果sem_op大于0,那么操作将sem_op加入到信号量的值中,并唤醒等待信号增加的进程.如果为0,当信号量的值是0的时候,函数返回,否则阻塞直到信号量的值为0.如果小于0,函数判断信号量的值加上这个负值.如果结果为0唤醒等待信号量为0的进程,如果小与0函数阻塞.如果大于0,那么从信号量里面减去这个值并返回16、 SystemV消息队列#include#incl

20、ude#includeintmsgget(key_tkey,intmsgflg);intmsgsnd(intmsgid,structmsgbuf*msgp,intmsgsz,intmsgflg);intmsgrcv(intmsgid,structmsgbuf*msgp,intmsgsz,longmsgtype,intmsgflg);intmsgctl(Intmsgid,intcmd,structmsqid_ds*buf);structmsgbuflongmsgtype;/*消息类型*/./*其他数据类型*/msgget函数和semget一样,返回一个消息队列的标志.msgctl和semctl是

21、对消息进行控制.msgsnd和msgrcv函数是用来进行消息通讯的.msgid是接受或者发送的消息队列标志.msgp是接受或者发送的内容.msgsz是消息的大小.结构msgbuf包含的内容是至少有一个为msgtype.其他的成分是用户定义的.对于发送函数msgflg指出缓冲区用完时候的操作.接受函数指出无消息时候的处理.一般为0.接收函数msgtype指出接收消息时候的操作.如果msgtype=0,接收消息队列的第一个消息.大于0接收队列中消息类型等于这个值的第一个消息.小于0接收消息队列中小于或者等于msgtype绝对值的所有消息中的最小一个消息.17、 SystemV共享内存#includ

22、e#include#includeintshmget(key_tkey,intsize,intshmflg);void*shmat(intshmid,constvoid*shmaddr,intshmflg);intshmdt(constvoid*shmaddr);intshmctl(intshmid,intcmd,structshmid_ds*buf);shmget和shmctl没有什么好解释的.size是共享内存的大小.shmat是用来连接共享内存的.shmdt是用来断开共享内存的.不要被共享内存词语吓倒,共享内存其实很容易实现和使用的.shmaddr,shmflg我们只要用0代替就可以了.

23、在使用一个共享内存之前我们调用shmat得到共享内存的开始地址,使用结束以后我们使用shmdt断开这个内存.18、 线程的创建和使用#includeintpthread_create(pthread_t*thread,pthread_attr_t*attr,void*(*start_routine)(void*),void*arg);voidpthread_exit(void*retval);intpthread_join(pthread*thread,void*thread_return);pthread_create创建一个线程,thread是用来表明创建线程的ID,attr指出线程创建时

24、候的属性,我们用NULL来表明使用缺省属性.start_routine函数指针是线程创建成功后开始执行的函数,arg是这个函数的唯一一个参数. 表明传递给start_routine的参数.pthread_exit函数和exit函数类似用来退出线程.这个函数结束线程,释放函数的资源,并在最后阻塞,直到其他线程使用pthread_join函数等待它. 然后将*retval的值传递给*thread_return.由于这个函数释放所以的函数资源,所以retval不能够指向函数的局部变量.pthread_join和wait调用一样用来等待指定的线程.19、 网络编程netstat命令netstat是用来

25、显示网络的连接,路由表和接口统计等网络的信息.telnettelnet是一个用来远程控制的程序,20、 函数intsocket(intdomain,inttype,intprotocol)domain:说明我们网络程序所在的主机采用的通讯协族(AF_UNIX和AF_INET等).AF_UNIX只能够用于单一的Unix系统进程间通信,而AF_INET是针对Internet的,因而可以允许在远程主机之间通信(当我们mansocket时发现domain可选项是PF_*而不是AF_*,因为glibc是posix的实现所以用PF代替了AF,不过我们都可以使用的).type:我们网络程序所采用的通讯协议(

26、SOCK_STREAM,SOCK_DGRAM等)SOCK_STREAM表明我们用的是TCP协议,这样会提供按顺序的,可靠,双向,面向连接的比特流.SOCK_DGRAM表明我们用的是UDP协议,这样只会提供定长的,不可靠,无连接的通信.protocol:由于我们指定了type,所以这个地方我们一般只要用0来代替就可以了socket为网络通讯做基本的准备.成功时返回文件描述符,失败时返回-1,看errno可知道出错的详细情况.intbind(intsockfd,structsockaddr*my_addr,intaddrlen)sockfd:是由socket调用返回的文件描述符.addrlen:是

27、sockaddr结构的长度.my_addr:是一个指向sockaddr的指针.在中有sockaddr的定义structsockaddrunisgnedshortas_family;charsa_data14;structsockaddr_inunsignedshortsin_family;unsignedshortintsin_port;structin_addrsin_addr;unsignedcharsin_zero8;我们主要使用Internet所以sin_family一般为AF_INET,sin_addr设置为INADDR_ANY表示可以和任何的主机通信,sin_port是我们要监听的

28、端口号.sin_zero8是用来填充的.bind将本地的端口同socket返回的文件描述符捆绑在一起.成功是返回0,失败的情况和socket一样intlisten(intsockfd,intbacklog)sockfd:是bind后的文件描述符.backlog:设置请求排队的最大长度.当有多个客户端程序和服务端相连时,使用这个表示可以介绍的排队长度.listen函数将bind的文件描述符变为监听套接字.返回的情况和bind一样.intaccept(intsockfd,structsockaddr*addr,int*addrlen)sockfd:是listen后的文件描述符.addr,addrl

29、en是用来给客户端的程序填写的,服务器端只要传递指针就可以了.bind,listen和accept是服务器端用的函数,accept调用时,服务器端的程序会一直阻塞到有一个客户程序发出了连接.accept成功时返回最后的服务器端的文件描述符,这个时候服务器端可以向该描述符写信息了.失败时返回-1intconnect(intsockfd,structsockaddr*serv_addr,intaddrlen)sockfd:socket返回的文件描述符.serv_addr:储存了服务器端的连接信息.其中sin_add是服务端的地址addrlen:serv_addr的长度connect函数是客户端用来

30、同服务端连接的.成功时返回0,sockfd是同服务端通讯的文件描述符失败时返回-1.21、 字节转换函数unsignedlonginthtonl(unsignedlonginthostlong)unsignedshortinthtons(unisgnedshortinthostshort)unsignedlongintntohl(unsignedlongintnetlong)unsignedshortintntohs(unsignedshortintnetshort)在这四个转换函数中,h代表host,n代表network.s代表shortl代表long第一个函数的意义是将本机器上的long数

31、据转化为网络上的long.22、 IP和域名转换structhostent*gethostbyname(constchar*hostname)structhostent*gethostbyaddr(constchar*addr,intlen,inttype)在中有structhostent的定义structhostentchar*h_name;/*主机的正式名称*/char*h_aliases;/*主机的别名*/inth_addrtype;/*主机的地址类型AF_INET*/inth_length;/*主机的地址长度对于IP4是4字节32位*/char*h_addr_list;/*主机的IP地

32、址列表*/#defineh_addrh_addr_list0/*主机的第一个IP地址*/gethostbyname可以将机器名(如)转换为一个结构指针.在这个结构里面储存了域名的信息gethostbyaddr可以将一个32位的IP地址(C0A80001)转换为结构指针.这两个函数失败时返回NULL且设置h_errno错误变量,调用h_strerror()可以得到详细的出错信息23、 字符串的IP和32位的IP转换intinet_aton(constchar*cp,structin_addr*inp)char*inet_ntoa(structin_addrin)函数里面a代表asciin代表ne

33、twork.第一个函数表示将a.b.c.d的IP转换为32位的IP,存储在inp指针里面.第二个是将32位IP转换为a.b.c.d的格式.24、 服务信息函数intgetsockname(intsockfd,structsockaddr*localaddr,int*addrlen)intgetpeername(intsockfd,structsockaddr*peeraddr,int*addrlen)structservent*getservbyname(constchar*servname,constchar*protoname)structservent*getservbyport(int

34、port,constchar*protoname)structserventchar*s_name;/*正式服务名*/char*s_aliases;/*别名列表*/ints_port;/*端口号*/char*s_proto;/*使用的协议*/25、 网络文件操作ssize_twrite(intfd,constvoid*buf,size_tnbytes)write函数将buf中的nbytes字节内容写入文件描述符fd.成功时返回写的字节数.失败时返回-1.并设置errno变量.在网络程序中,当我们向套接字文件描述符写时有俩种可能.1)write的返回值大于0,表示写了部分或者是全部的数据.2)返

35、回的值小于0,此时出现了错误.我们要根据错误类型来处理.如果错误为EINTR表示在写的时候出现了中断错误.如果为EPIPE表示网络连接出现了问题(对方已经关闭了连接).ssize_tread(intfd,void*buf,size_tnbyte)read函数是负责从fd中读取内容.当读成功时,read返回实际所读的字节数,如果返回的值是0表示已经读到文件的结束了,小于0表示出现了错误.如果错误为EINTR说明读是由中断引起的,如果是ECONNREST表示网络连接出了问题.structmy_structmy_struct_client;write(fd,(void*)&my_struct_cli

36、ent,sizeof(structmy_struct);/*服务端的读*/charbuffersizeof(structmy_struct);struct*my_struct_server;read(fd,(void*)buffer,sizeof(structmy_struct);my_struct_server=(structmy_struct*)buffer;intrecvfrom(intsockfd,void*buf,intlen,unsignedintflags,structsockaddr*fromint*fromlen)intsendto(intsockfd,constvoid*m

37、sg,intlen,unsignedintflags,structsockaddr*tointtolen)sockfd,buf,len的意义和read,write一样,分别表示套接字描述符,发送或接收的缓冲区及大小.recvfrom负责从sockfd接收数据,如果from不是NULL,那么在from里面存储了信息来源的情况,如果对信息的来源不感兴趣,可以将from和fromlen设置为NULL.sendto负责向to发送信息.此时在to里面存储了收信息方的详细资料.26、 高级套接字函数读写操作.intrecv(intsockfd,void*buf,intlen,intflags)intsen

38、d(intsockfd,void*buf,intlen,intflags)前面的三个参数和read,write一样,第四个参数可以是0或者是以下的组合_|MSG_DONTROUTE|不查找路由表|MSG_OOB|接受或者发送带外数据|MSG_PEEK|查看数据,并不从系统缓冲区移走数据|MSG_WAITALL|等待所有数据|-|MSG_DONTROUTE:是send函数使用的标志.这个标志告诉IP协议.目的主机在本地网络上面,没有必要查找路由表.这个标志一般用网络诊断和路由程序里面.MSG_OOB:表示可以接收和发送带外的数据.关于带外数据我们以后会解释的.MSG_PEEK:是recv函数的使

39、用标志,表示只是从系统缓冲区中读取内容,而不清楚系统缓冲区的内容.这样下次读的时候,仍然是一样的内容.一般在有多个进程读写数据时可以使用这个标志.MSG_WAITALL是recv函数的使用标志,表示等到所有的信息到达时才返回.使用这个标志的时候recv回一直阻塞,直到指定的条件满足,或者是发生了错误.1)当读到了指定的字节时,函数正常返回.返回值等于len2)当读到了文件的结尾时,函数正常返回.返回值小于len3)当操作发生错误时,返回-1,且设置错误为相应的错误号(errno)如果flags为0,则和read,write一样的操作.还有其它的几个选项,不过我们实际上用的很少,可以查看Linu

40、xProgrammersManual得到详细解释.intrecvmsg(intsockfd,structmsghdr*msg,intflags)intsendmsg(intsockfd,structmsghdr*msg,intflags)structmsghdrvoid*msg_name;intmsg_namelen;structiovec*msg_iov;intmsg_iovlen;void*msg_control;intmsg_controllen;intmsg_flags;structiovecvoid*iov_base;/*缓冲区开始的地址*/size_tiov_len;/*缓冲区的长

41、度*/msg_name和msg_namelen当套接字是非面向连接时(UDP),它们存储接收和发送方的地址信息.msg_name实际上是一个指向structsockaddr的指针,msg_name是结构的长度.当套接字是面向连接时,这两个值应设为NULL.msg_iov和msg_iovlen指出接受和发送的缓冲区内容.msg_iov是一个结构指针,msg_iovlen指出这个结构数组的大小.msg_control和msg_controllen这两个变量是用来接收和发送控制数据时的msg_flags指定接受和发送的操作选项.和recv,send的选项一样intshutdown(intsockfd,inthowto)TCP连接是双向的(是可读写的),当我们使用close时,会把读写通道都关闭,有时侯我们希望只关闭一个方向,这个时候我们可以使用shutdown.针对不同的howto,系统回采取不同的关闭方式.howto=0这个时候系统会关闭读通道.但是可以继续往接字描述符写.howto=1关闭写通道,和上面相反,着时候就只可以读了.howto=2关闭读写通道,和close一样在多进程程序里面,如果有几个子进程共享一个套接字时,如果我们使用shutdown,那么所有的子进程都不能够操作了,这个时候我们只能够使用close来关闭子进程的套接字描述符.

展开阅读全文
温馨提示:
1: 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
2: 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
3.本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
5. 装配图网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
关于我们 - 网站声明 - 网站地图 - 资源地图 - 友情链接 - 网站客服 - 联系我们

copyright@ 2023-2025  zhuangpeitu.com 装配图网版权所有   联系电话:18123376007

备案号:ICP2024067431-1 川公网安备51140202000466号


本站为文档C2C交易模式,即用户上传的文档直接被用户下载,本站只是中间服务平台,本站所有文档下载所得的收益归上传人(含作者)所有。装配图网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对上载内容本身不做任何修改或编辑。若文档所含内容侵犯了您的版权或隐私,请立即通知装配图网,我们立即给予删除!