竞争状态是这样一种情形:操作共享资源的两个进程(或线程),其结果取决于一个无法预期的顺序,即这些进程获得CPU使用权的先后相对顺序。

以独占的方式创建一个文件

当同时指定了O_EXCL和O_CREAT作为open的标志位时,如果要打开的文件已经存在,则open将返回一个错误。

这种机制为了保证进程是打开文件的创建者。

对文件是否存在的检查和创建属于同一原子操作。、

如果不实用O_EXCL标志的话,要调用两次open,以此判断文件是否存在,一个是创建一个文件。

但有个情况是:

当第一次调用open时,希望打开的文件还不存在,而当第二次调用open时,其他进程已经创建了该文件。

如下图,若内核调度器判断出分配给A进程的时间片已经耗尽,并且将CPU的使用权交给B进程,就有肯能发生这种问题。

再比如两个进程在一个多CPU系统上同时运行,也会出现这种情况。

在这种情况下,A会认为目标文件是由自己创建的。因为不论目标文件存在与否,进程A对open的第二次调用都会成功。

由于第一个进程在检查文件是否存在和创建文件之间发生了中断,造成两个进程都声称自己是文件的创建者。

结合O_CREAT和O_EXCL标志来一次性地调用open可以防止这种情况,因为这确保了检查和创建文件的捕捉属于一个单一的原子(不可中断的)操作。

向文件尾部追加数据

说明原子操作的第二个例子是:多个进程文件同时同一个文件(例如,全局日志文件)尾部添加数据。

每次写入新的日志时,会用lseek将文件偏移量设置到文件尾部,然后再写入数据。

但是在lseek和write之间会被其他进程所打断,那么这两个进程在写入数据前,将文件偏移量设为相同位置,而当第一个进程再次获得调度时,会覆盖第二个进程已写入的数据。此时再次出现了竞争状态,因为执行的结果依赖于内核对两个进程的调度顺序。

要规避这一个问题,需要将文件偏移量的移动与数据写入操作纳入同一个原子操作。在打开文件时加入O_APPEND标志就可以保证这一点。

注意了,在打开文件时加入O_APPEND标志。所以这个意思就是,打开之后的写都是先移到文件末尾,在写数据咯?

Unix系统编程()原子操作和竞争条件的更多相关文章

  1. 《Linux/Unix系统编程手册》读书笔记2

    <Linux/Unix系统编程手册>读书笔记 目录 第5章: 主要介绍了文件I/O更深入的一些内容. 原子操作,将一个系统调用所要完成的所有动作作为一个不可中断的操作,一次性执行:这样可以 ...

  2. 《Linux/UNIX系统编程手册》第63章 IO多路复用、信号驱动IO以及epoll

    关键词:fasync_helper.kill_async.sigsuspend.sigaction.fcntl.F_SETOWN_EX.F_SETSIG.select().poll().poll_wa ...

  3. 《Linux/Unix系统编程手册》读书笔记 目录

    <Linux/Unix系统编程手册>读书笔记1  (创建于4月3日,最后更新4月7日) <Linux/Unix系统编程手册>读书笔记2  (创建于4月9日,最后更新4月10日) ...

  4. 《Linux/Unix系统编程手册》读书笔记9(文件属性)

    <Linux/Unix系统编程手册>读书笔记 目录 在Linux里,万物皆文件.所以文件系统在Linux系统占有重要的地位.本文主要介绍的是文件的属性,只是稍微提及一下文件系统,日后如果有 ...

  5. 《Linux/Unix系统编程手册》读书笔记8 (文件I/O缓冲)

    <Linux/Unix系统编程手册>读书笔记 目录 第13章 这章主要将了关于文件I/O的缓冲. 系统I/O调用(即内核)和C语言标准库I/O函数(即stdio函数)在对磁盘进行操作的时候 ...

  6. 《Linux/Unix系统编程手册》读书笔记7 (/proc文件的简介和运用)

    <Linux/Unix系统编程手册>读书笔记 目录 第11章 这章主要讲了关于Linux和UNIX的系统资源的限制. 关于限制都存在一个最小值,这些最小值为<limits.h> ...

  7. 《Linux/Unix系统编程手册》读书笔记6

    <Linux/Unix系统编程手册>读书笔记 目录 第9章 这章主要讲了一堆关于进程的ID.实际用户(组)ID.有效用户(组)ID.保存设置用户(组)ID.文件系统用户(组)ID.和辅助组 ...

  8. 《Linux/Unix系统编程手册》读书笔记5

    <Linux/Unix系统编程手册>读书笔记 目录 第8章 本章讲了用户和组,还有记录用户的密码文件/etc/passwd,shadow密码文件/etc/shadow还有组文件/etc/g ...

  9. 《Linux/Unix系统编程手册》读书笔记4

    <Linux/Unix系统编程手册>读书笔记 目录 第7章: 内存分配 通过增加堆的大小分配内存,通过提升program break位置的高度来分配内存. 基本学过C语言的都用过mallo ...

  10. 《Linux/Unix系统编程手册》读书笔记3

    <Linux/Unix系统编程手册>读书笔记 目录 第6章 这章讲进程.虚拟内存和环境变量等. 进程是一个可执行程序的实例.一个程序可以创建很多进程. 进程是由内核定义的抽象实体,内核为此 ...

随机推荐

  1. 配置文件格式用哪个?文件夹+纯文本文件,XML,SQLite

    稍具规模的软件都会须要一个配置文件来支持软件的执行.眼下常见的配置文件格式有纯文本.XML.SQLite.自己定义二进制格式,怎样进行选择呢? 1 纯文本--永远不会失效的文件格式 文本化是传统Uni ...

  2. [Swift A] - Welcome to Swift

    Swift is a new object-oriented programming language for iOS and OS X development. Swift is modern, p ...

  3. springmvc处理流程

    SpringMVC核心处理流程: 1.DispatcherServlet前端控制器接收发过来的请求,交给HandlerMapping处理器映射器 2.HandlerMapping处理器映射器,根据请求 ...

  4. dubbo初探(转载)

    1. Dubbo是什么? Dubbo是一个分布式服务框架,致力于提供高性能和透明化的RPC远程服务调用方案,以及SOA服务治理方案.简单的说,dubbo就是个服务框架,如果没有分布式的需求,其实是不需 ...

  5. ssh-keygen - 生成、管理和转换认证密钥

    通常使用:[b]ssh-keygen -i -f 公密匙名>> authorized_keys[/b]语法详细介绍[code]ssh-keygen [-q] [-b bits] -t ty ...

  6. iOS GZWaterfall任何形式的瀑布流

    概述 使用UICollectionView可以布局各种各样的瀑布流,下面我写了几种不同布局的瀑布流样式 详细 代码下载:http://www.demodashi.com/demo/11018.html ...

  7. quartus ii工程文件的分析

    .pof:通过AS口将程序固化到EPCS(flash)内. .sof:通过JTAG口下载到FPGA内部的SRAM里面. .JIC:通过JTAG口将程序固化到EPCS(flash)内.

  8. NAT Network Address Translation,网络地址转换

    Network Address Translation,网络地址转换

  9. spring中ApplicationContext

    1 spring 容器应用上下文:ApplicationContext 主要的实现类是 ClassPathXmlApplicationContext 和 FileSystemXmlApplicatio ...

  10. css 只改变父元素的透明度,不改变子元素透明度rgba+opacity

    给元素加透明度时,通常写法为:opacity:0.5,filter:alpha(opacity=50); 我们通常也会遇到,在给父元素背景设置透明度时,子元素内容继承了父元素的透明度. 如何让子元素脱 ...