【问题标题】:How to calculate the bit flags/enum flags for oflag in open()?如何计算open()中oflag的位标志/枚举标志?
【发布时间】:2010-02-18 22:03:33
【问题描述】:

我正在处理一项网络任务,我们的任务是使用给定的协议创建一个远程文件访问服务器。我的困难在于我找不到解释在 open() 中为oflag 参数计算位的过程的信息。

我收到来自客户端的消息以打开文件,并在消息中解析字符以供在 oflag 中使用的标志。具体是:

  • R - O_RDONLY
  • W - O_WRONLY
  • RW - O_RDWR
  • A - O_APPEND
  • C - O_CREAT
  • T - O_TRUNC
  • E - O_EXCL

我在 Google 上转了一圈,搜索了按位运算、枚举标志、位标志、计算位标志等,但找不到对弄清楚如何为 oflag 创建位有用的东西。也许我只是不知道自己在寻找什么而忽略了有用的信息?

有人可以吗:

  • 为我指明方向/提供指向文档的链接/如何计算位数的示例/# 鉴于我的已解析字符,我应该放入 oflags 或
  • 告诉我标志的枚举类型和它们应该进入的顺序

非常感谢您的帮助,如果我不清楚我的问题或我想要做什么,请告诉我,我会尽快澄清。

【问题讨论】:

    标签: c linux unix


    【解决方案1】:

    O_... 标志是数字,每个都具有不同的单个位集。例如在我的系统上,它们在fcntl.h 中定义为

    #define O_RDONLY             00
    #define O_WRONLY             01
    #define O_RDWR               02
    #define O_CREAT            0100 /* not fcntl */
    #define O_EXCL             0200 /* not fcntl */
    #define O_NOCTTY           0400 /* not fcntl */
    #define O_TRUNC           01000 /* not fcntl */
    #define O_APPEND          02000
    

    您使用|(逻辑或)组合标志并将单个数字传递给open,并为您想要的每个选项设置所有位。所以例如open("file", O_RDWR | O_CREAT).

    如果需要,您也可以计算一个 int 并将其传递给 open。

    int flags = 0;
    if (...)
        flags |= O_RDWR;
    ...
    open('file', flags);
    

    【讨论】:

    • 例如,如果我解析了 RWC,那么它将是 open("file", O_RDWR | O_CREAT)。但是因为只知道字符我会做类似 int oflag = (02 | 0100) 的事情,然后我的 open 看起来像 open("file", oflag)?我需要从我解析的字符转换为二进制。
    【解决方案2】:

    通常的表达方式类似于O_RDWR | O_CREAT。请注意O_RDWR 正是O_RDONLY | O_WRONLY

    你可以这样做:

    char *flags = "r";
    int oflag = 0;
    
    if (strchr(flags,'r')) oflag |= O_RDONLY;
    

    其余的标志以此类推。

    【讨论】:

    • 嗯...也许我有点困惑。假设我想用 O_WRONLY | 打开一个文件O_CREAT | O_APPEND,会在那里以及如何计算一些 int/bits 放入?例如,我可以输入对应于那些 flgas 的 open("myfile", ) 吗?
    • @Chris:使用标志,而不是数字。在这种情况下,您将使用 open("myfile", O_WRONLY | O_CREAT | O_APPEND)。如果没有别的,它更容易阅读。
    • 使用标志...这些标志位并非全部标准化,因此您不能假设它们在每个平台上都具有相同的值。此外,符号形式更具可读性,因此可维护......源代码是为了您的利益,而不是机器的。
    • @Andrew,评论“O_RDWR 完全是 O_RDONLY | O_WRONLY”是错误的。在大多数情况下,O_RDONLY 是 (00) O_WRONLY 是 (01),因此 O_RDONLY| O_WRONLY 是 (01) 。它与 (02) 的 O_RDWR 不同
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-01-14
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-04-01
    • 1970-01-01
    相关资源
    最近更新 更多