Linux网络编程学习记录

          在1981年之前,计算机是大型企业和政府部门才能使用的昂贵设备,IBM公司在1981年推出个人计算机IBM PC,从此个人计算机得以发展。当时大型机上面跑的是UNix系统,但是unix收费昂贵且不开源,为了在个人计算机上使用操作系统,后面出现了Minix,再后来出现了Linux。

        对Linux的发展起到重要帮助的有:Unix操作系统,minix操作系统,GNU计划,POSIX标准,Internet网络。posxi标准是IEEE和ISO\IEC为Unix制定的标准,但是制定的时候,linux刚刚诞生,因此linux系统的接口与Posix完全兼容。

             Linux系统分为内核空间和用户空间,内核空间由5个子系统组成

①进程调度         ②内存管理          ③虚拟文件系统          ④网络接口          ⑤进程间通信。

一、shell命令

1.普通用户和超级用户视图

   su: 进入超级用户,需要输入root密码

   sudo passwd root :设置root用户密码

   exit: 退回普通用户

2.文件系统

    fdisk -l :查看当前磁盘的情况

     ls -li  hello.c:可以查看hello.c文件索引号

    ln hello.c hello2.c:创建一个硬链接,hello.c和hello2.c使用同一个索引号,改变一个hello.c中的内容hello2.c的内容也会改变。但是删除hello.c,hello2.c不会被删除。只有文件才能创建硬链接,目录不能。但是目录可以使用ln-s创建软链接。

3.查看进程树pstree。

二、进程调度scheding

1.定义:进程调度是指系统对进程的多种状态之间的转换策略。Linux下的进程调度策略有三种:

①SHCHED_OTHETR        ②SCHED_FIFO        ③SCHED_RR

a.SHCHED_OTHETR :普通进程的时间片轮转调度策略,这种策略中,系统给所以运行状态的进程分配时间片,在当前进程的时间片用完之后,系统从剩下的进程中选择优先级高的进程运行。

b.SCHED_FIFO  : 是针对实时性要求高但是运行时间短的进程,这种策略中系统按照进入队列的先后顺序进行进程的调度,在没有高优先级进程中断和阻塞的情况下,会一直运行。

c.SCHED_RR: 是针对实时性要求高且运行时间长的进程,与SHCHED_OTHETR 的策略类似,只不过RR进程的优先级高很多,系统分配给RR进程时间片,然后轮询运行这些进程,将时间片用完的进程放入队列的末尾。

三、内存管理MMU

        内存管理是多个进程之间的内存共享策略,Linux系统中的内存是指虚拟内存,每个进程拥有相同的内存空间,通常虚拟内存是物理内存的两倍

四、虚拟文件系统VRF

在Linux下支持多种文件系统,如ext、ext2、ext3、minix等等,目前常用的是ext2和ext3,ext2文件系统用于固定文件系统和可活动文件系统,是ext系统的扩展,ext3文件系统是在ext2上增加日志功能扩展后的扩展,兼容ext2,可以互相转换。

unix下一切皆文件,在linux下对磁盘进行操作的工具是fdisk,与windows下面的fdisk功能类似,但是命令格式不同,通过fdisk -l可以查看当前磁盘的情况。

a.文件分类

①普通文件: 这种文件的特性是数据在存储设备上,内核提供对数据的抽象访问,此文件为一种字节流,访问接口完全独立于磁盘上的存储数据。例如C文件,可执行文件,目录等。

     操作:对文件进行打开,读出数据,写入数据,关闭,删除。

②字符设备文件c:是一种能够像文件一样能够被访问的设备,例如控制台,串口

   设备文件都有三个属性:①设备类型(字符设备c,块设备b)②主设备号   ③次设备号

 ③块设备文件b:与普通文件的区别是操作系统对数据的访问格式会重新设计,例如磁盘。

④socket文件:是为了实现网络通信的一种文件,对网络的访问可以通过文件描述符的抽象实现,访问与普通文件类似。

文件的两个属性:索引节点inode和块block,将一个文件比喻成一本书的话,inode相当于书的目录,block相当于书的内容。inode在linux系统中是唯一的。命令ls -li hello.c可以查看hello.c的索引号。

Linux文件系统用一组通用对象表示:

①超级块(superblock)②节点索引(inode)③目录结构(dentry) ④文件(file)

b.文件描述符

Linux用文件描述符表示作为唯一识别一个文件的ID号,文件描述符是一个int的整数。文件描述符的取值范围为0---Open_Max,所以打开了文件后需要调用close()函数释放。如果打开的文件数量超过了Open_Max,则会造成打开失败。经过测试在ubuntu上Open_Max=1023,最多从3-1023可用

文件描述符只在一个进程中有效,因此用一个描述符在不同进程之间,可能描述的是不同的文件。

Linux下有三个已经分配了的文件描述符,标准输入stdin=0,标准输出stdout=1,标准错误stderr=2

因此第一个被打开的文件的文件描述符是3。

c.常用文件操作函数

1.打开文件open

int open(const char *pathname,int flags,mode_t mode);

打开成功则返回整形文件描述符fd,失败返回-1。

flags:用于打开后运行对文件操作的方式,只读,只写,可读可写,是在宏定义号了的。                 只读O_RDONLY=0,只写O_WRONLY=1,读写O_RDWR=2。

mode:表示用户、组用户、其他用户对文件的读写权限,可以省略。

2.关闭文件close

int close(int f);

关闭文件描述符后,此文件描述符不在指向任何文件,因此此文件描述符可以再次使用,close调用成功返回0,失败返回-1,

3.读文件内容

ssize_t read(int fd, void *buff, size_t count);

执行成功返回实际读取到的字节数,可能会小于请求字节数count,失败返回-1,如果读到文件末尾返回0。

ssize_t:可能是long,int,表示实际读取到的字节数。

形参fd:表示通常是open().creat()返回的值。

形参buff:指向缓冲区的起始地址,读入的数据保持在这个缓冲区中。

形参count:表示请求读取的字节数。count需要小于buff的大小,否者会产生溢出。

4.向文件写内容

ssize_t write(int fd, void *buff, size_t count);

向文件描述符fd写入count字节数的数据,数据来源于buff指针指向的数据。

写操作并不能保证将数据成功的将数据写入磁盘中,这在异步操作中经常出现,write函数通常将数据写入缓冲区,在合适的实际由系统写入实际的设备,可以调用fsync函数,显示将输入写入设备。

5.文件偏移函数

off _t lseek(int fildes,off_t offset ,int whence)

offset: 偏移量           whence: 来源

调用成功,则返回新的文件偏移量的值,失败则返回-1,由于offset可以为负值,所以判断是否调用成功,可以使用是否等于-1来判断,而不是小于0来判断。

6.获取文件状态的函数

int stat (const char *path, struct stat *buff);

int fstat(int filedes, struct stat *buff);

int lstat(const char *path, struct stat *buff);

函数的第一个参数是文件描述符或者文件的路径,buff为指向struct stat的指针,获得的状态从这个参数中传回。调用成功返回0,失败返回-1。

7.内存映射函数

void *mmap(void *start,   size_t length,   int prot,   int flags,  int fd off_t offset);

函数功能:是将文件或者设备空间映射到内存中去,因此在磁盘上存取文件的操作转换为内存上存取文件的操作,由于内存比磁盘快,因此提高了读写速度。

参数说明:start通常为NULL,由系统自己决定映射到什么地址。length表示被映射数据的长度,

                port表示映射区保护方式,flags用于设定映射对象的类型、选项、和是否可以对映射对象进行读写等。port和flags均为组合值。fd表示文件的文件描述符,表示要映射到内存中的文件,offset表示开始于offset大小为length的区域。

int munmap(void *start, size_t lenght);

函数功能:取消mmap函数的映射关系,start为mmap函数成功后返回的值,即内存的地址,length为映射的长度。

8.文件属性函数fcntl()

int fcntl(int fd, int cmd)

int fcntl(int fd, int cmd, long arg)

int fcntl(int fd, int cmd, struct flock *lock);

函数fcntl向已经打开的文件fd发送命令,更改其属性。

9.文件输入输出函数ioctl()

int ioctl(int d, int request, ......)

ioctl像其他函数一样,打开文件,发送命令,查询结果,ioctl函数像一个杂货铺一样,对设备的控制通常都是通过这个函数来实现的。对设备的具体操作方式,由设备的驱动程序决定。

五、网络接口

        网络接口是为了物理设备通信而产生的,网络接口包括驱动程序和网络协议,驱动程序是对硬件设备的驱动,网络协议是网络传输的通信标准。所以目前的网络设备几乎都有驱动程序。

六、进程间通信

Linux支持多进程,进程之间需要通信,Linux的进程间通信是从Unix继承过来的,Linux下的进程间通信主要有:①管道pipe ②信号signal ③消息队列queque ④共享内存 ⑤套接字socket

①半双工管道:和RX和TX串口通信类似,都是半双工通信,A---内核——B

特点:具有阻塞性和原子性

函数:

①pipe:创建管道

②命令管道FIFO:和半双工管道的在IO操作上是一样的,只是FIFO需要调用一个open函数。

③ 消息队列:消息是内核地址空间中的内部链表,消息顺序的发送到消息队列中去,并以几种不同方式从队列中获取,每个消息队列可以用IPC标识符唯一的进行标识。

④信号量:是一种计数器,用来控制多个进程共享的资源所进行的访问,通常用做锁lock/unlock机制,典型模型是生产者和消费者模型。

函数:①semget:新建信号量函数

          ②semop:信号量操作函数

          ③semctl: 信号量控制函数

  ⑤共享内存:是多个进程之间共享内存区域的的通信方式,是进程通过对内存段进行映射的方实现内存共享的。这是IPC最快捷的方式,因为没有中间过程,多个进程的共享内存是同一块物理空间,仅仅是地址不同而已,因此不需要复制,就可以直接操作此段空间。

函数:①shmget:创建共享内存函数

          ②shmat:获得共享内存地址的函数

          ③shmdt:删除共享内存的函数

          ④shmctl:共享内存控制函数

⑥信号:信号机制是UNIX中最古老的通信方式之一,它作用于在多个进程之间传递异步信号,信号可以由各种中断产生,shell也可以使用信号将作业控制命令传递给它的子进程。

七、常识概念

1.GNU通用许可证(简称GPL),是由自由软件基金会发行的用于计算机软件的一种许可制度。

2.Linux的文件结构:是以/为根的树结构,每增加一个为文件,就将其加入到这个树中来。

3.gcc编译器四大步骤:①预编译 ②编译和优化 ③汇编 ④链接

4.makefile文件简绍: 当项目有多个文件时,gcc显得不方便,gcc对单个文件方便,借助Linux下的make工具,去解释makefile文件。

5.应用程序、进程、线程

应用程序:是源程序经过编译后的可执行程序,是存放在磁盘上的,还没有运行。

进程:从用户的角度看是应用程序的执行过程。从操作系统来看是操作系统分配内存、cpu时间片等资源的最小单位,是为正在运行的程序提供运行环境。

线程:是为了节约资源可以在同一个进程中共享资源的执行单位。

进程和线程的区别:

进程是操作系统进行资源分配的基本单位,拥有完整的虚拟空间。线程操作系统只分配cpu资源,其余内存等资源需要共享。多线程之间的共享方式比多进程之间的共享方式多。进程有进程控制表PCB,系统通过PCB对进程进行调度,线程有线程控制表TCB,系统通过TCB对进程进行调度,但是TCB所表示的状态比PCB少很多。

6.进程号:操作系统为每一个进程分配一个进程号,用于唯一标识一个进程,称为PID,类型为pid_t。

7.线程:和进程相比,线程由三点优势:①系统资源消耗低,②速度快,③线程间数据共享比进程容易得多。linux下的多线程遵循POSIX标准,叫做pthread,编写linux下的线程需要包含头文件pthread.h,在生成可执行文件的时候,需要链接库libpthread.或者libpthread.so.

函数:①pthread_create:创建线程

           ②pthread_join:等待一个线程运行的结束

           ③pthread_exit:结束线程

相关概念:①线程的属性结构

                ②线程的优先级

                ③线程的绑定状态

                ④线程的分离状态

                ⑤线程间的互斥

线程中使用信号量:函数①sem_init:初始化一个信号量

                                       ②sem_post:增加信号量的值,每次增加1,当有线程等待这个信号的时候,等待的线程将返回。

                                        ③sem_wait:减少信号量的值,如果信号量的值为0,则线程会一直阻塞到信号量的值大于0为止。

                                        ④sem_destroy:线程信号量销毁函数。

8.对程序、进程、线程的总结:程序和进程之间的区分在于程序是静态的,进程和线程的动态的。线程是轻量级的进程。进程的产生和消亡对操作系统来说,就是占用资源和释放资源。LInux进程中没有POSXI规定的挂起,恢复运行等机制。

八、干活工具

1.编辑器:VIM是vi的扩展,vi是unix下最通用的文本编辑器。

2.编译器:gcc\g++:c/c++语言编译器,输入源文件,输出可执行文件.

                   支持交叉编译。www.gun.org见详情

3.调试器:gdb,用于调试c和c++程序

4.构建大项目时libtools和cmake:

九、进程操作

linux系统进程图是一个树结构,所有进程有一个共同的祖先init进程,这是树结构的根。其余的进程是父子,兄弟,堂兄弟的关系。新的进程不是被全新的创建,通常是从一个原有的进程进行复制或者克隆。可以在终端中使用pstree查看进程树。

linux下对进程的操作方式主要有①产生进程  ②终止进程 ③进程间通信 ④进程间数据同步

①产生进程:可以调用函数fork()、system()、exec()创建进程。

a.获取进程号函数

getpid(): 获取当前进程的进程号。

getppid():获取当前进程的父进程的ID号

b.①进程函数函数fork

pid_t fork(void): 以父进程为蓝本复制一个进程,父进程与子进程ID号不同,父进程与子进程只有内存不同,其余共享。fork函数是执行一次返回两次,父进程中返回子进程的ID号,在子进程中返回0;

②int system(cosnt chat *command)

system调用/bin/sh-c command 执行特定的的命令,阻塞当前进程直到command命令执行完毕。

执行system函数时,会调用fork、execve、waitpid函数,其中任一个调用失败,将导致system函数调用失败。失败返回-1,当sh不能执行的时候返回127,成功时返回进程状态值。

③exec函数族

extern char **environ;

int execl(const char *path,  const char *arg, ..);

int execlp(const char *file, const *arg, ...);

int execle(const char *path, const char *arg, ..char *const envp[]);

int execv(const char *path, char *const argv[]);

int execvp(cost char *file,  char *cosnt argv[]);

六个函数,只有execve函数是真正的被系统调用,其余五个都是在其基础上经过包装的库函数。

九、网络编程基础

1.TCP/IP协议:应用层协议HTTP:用于Web访问、FTP:用于文件传输协议、Telnet:用于远程主机的登录。这三种协议都是基于TCP协议的。NFS:是linux上经常使用的一种协议,用于主机之间共享文件,由于NFS协议是基于UDP协议的,所以速度快很多,NFS协议在嵌入式设备开发的时候进程使用,用于设备和主机之间共享文件系统。

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值