zoukankan      html  css  js  c++  java
  • 编写你的应用程序(六)、nacl_io库

    原文链接:https://developer.chrome.com/native-client/devguide/coding/nacl_io

    注意:已针对ChromeOS以外的平台公布了此处所述技术的弃用。
    请访问我们的 迁移指南 了解详情。


    nacl_io库

    介绍

    nacl_io是一个实用程序库,提供标准C API的实现,如POSIX I / O(stdio.h)和BSD套接字(sys/socket.h)。它的主要功能是允许在Native Client模块中编译和使用使用这些标准API的代码。该库作为Native Client SDK的一部分包含在内,并在Pepper API之上实现。

    由于Native Client模块无法直接访问主机的文件系统,因此nacl_io提供了几种可供应用程序使用的备用文件系统类型。例如,Chrome浏览器支持HTML5文件系统API ,该API提供对本地文件系统的受保护区域的访问。可以使用JavaScript命令通过HTML页面访问此文件系统,也可以使用Pepper File IO API通过Native Client模块访问此文件系统。

    与nacl_io一个本机客户端应用程序可以安装一个文件系统HTML5并经由标准POSIX I / O功能访问它如fopenfseek, freadfwrite,和fclose,或它们的低级别UNIX同行 openlseekreadwriteclose。除HTML5文件系统外,nacl_io还提供了其他几种文件系统类型,如下表所示:

    文件系统 描述
    MEMFS 内存中的文件系统
    html5fs HTML5本地文件系统,可以是持久的也可以是临时的
    HTTP 将远程Web服务器上的文件映射到本地文件系统。
    dev 含特殊文件的文件系统(例如:/dev/null

    使用nacl_io

    使用nacl_io主要是使用标准POSIX C库函数。但是,初始化库和设置文件系统安装需要一些步骤。通常,在NaCl应用中使用nacl_io需要以下步骤:

    1. 将应用程序与nacl_io库链接(-lnacl_io
    2. 使用nacl_io_init_ppapi或 nacl_io_init函数在启动时初始化nacl_io 。
    3. 使用该mount功能挂载任何所需的文件系统。mount有关不同文件系统类型的参数详见include/nacl_io/nacl_io.h
    4. 如果要安装HTML5文件系统,请确保为其分配空间。您可以unlimitedStorage在应用程序的Web Store清单文件中设置权限,也可以调用HTML5 QuotaManagement API。文件IO文档中介绍了这些选项。
    5. 确保文件和套接字API调用都是从后台线程完成的。这是因为主要的Pepper线程不支持POSIX I / O操作所需的阻塞行为。

    登录nacl_io

    与nacl_io的大多数输入/输出不同,内部日志记录直接写入stderrNaCl过程的 流。它故意绕过nacl_io中实现的标准库函数,以避免对自身进行循环调用。

    nacl_io演示

    构建并运行演示

    演示应用程序启动一个Native Client模块,该模块安装三个文件系统并显示一组控件,使您可以使用它们:

    /native-client/images/nacl_io1.png

    按照以下步骤构建并运行演示:

    • 在demo目录中打开一个终端:

      $ cd $NACL_SDK_ROOT/examples/demo/nacl_io_demo
    • 运行演示:

      $ make run

    演示运行后,请尝试以下操作:

    1. 选择fopen命令(当您选择命令时,下面一行中的字段将根据命令更改)
    2. 输入文件名 /persistent/test
    3. 选中写入复选框,然后按fopen按钮
    4. 选择fwrite命令并/persistent/test在左侧下方显示的菜单中选择文件
    5. 输入一些数据,然后按下fwrite按钮
    6. 选择fclose命令,确保/persistent/test在菜单中选择了文件,然后按fclose按钮
    7. 选择fopen命令
    8. 输入文件名 /persistent/test
    9. 选中fread复选框,然后按fopen按钮
    10. 选择fread命令,确保在菜单中选择文件/ persistent / test,输入字节数,然后按下fread按钮

    看一下代码

    该演示用C语言编写,包含三个文件。

    nacl_io_demo.c

    这是演示的主文件。此处的代码创建并初始化Native Client模块实例。Pepper函数Instance_DidCreate初始化nacl_io并在其中安装HTML5文件系统/persistent

    static PP_Bool Instance_DidCreate(PP_Instance instance,
                                      uint32_t argc,
                                      const char* argn[],
                                      const char* argv[]) {
      g_instance = instance;
      nacl_io_init_ppapi(instance, get_browser_interface);
      mount(
          "",  /* source */
          "/persistent",  /* target */
          "html5fs",  /* filesystemtype */
          0,  /* mountflags */
          "type=PERSISTENT,expected_size=1048576");  /* data specific to the html5fs type */
    
      pthread_create(&g_handle_message_thread, NULL, &HandleMessageThread, NULL);
      InitializeMessageQueue();
    
      return PP_TRUE;
    }

    /persistent初始化模块后,会为文件系统分配空间。这是通过domContentLoaded文件中的函数完成的example.js。该脚本包含在模块的html页面中(请参阅参考资料 examples/demo/index.html):

    function domContentLoaded(name, tc, config, width, height) {
      navigator.webkitPersistentStorage.requestQuota(window.PERSISTENT, 1024 * 1024,
          function(bytes) {
            common.updateStatus(
                'Allocated ' + bytes + ' bytes of persistent storage.');
            common.createNaClModule(name, tc, config, width, height);
            common.attachDefaultListeners();
          },
          function(e) { alert('Failed to allocate space') });
    }

    Instance_DidCreate函数还创建一个工作线程,该线程接收从html页面发送的消息并执行指定的文件系统操作。工作线程的逻辑在其他两个文件中编码,如下所述。

    queue.c

    此文件实现了一个循环队列,用于从浏览器UI接收消息到Native Client模块。排队消息中的文件系统命令在工作线程上执行。这样可以阻止主要Native Client线程的调用(如fread),这是一件好事。队列在nacl_io_demo.c中初始化Instance_DidCreate

    handlers.c

    此文件实现与从浏览器发送的命令关联的stdio调用。Handle*每个命令都有一个单独的函数:fopen,fclose,fseek,fread,fwrite。处理程序从HandleMessagenacl_io_demo.c中的函数调用,该 函数在管理消息队列的工作线程中运行。fwrite处理程序的代码如下所示。请注意,它不包含任何PPAPI调用,看起来像“普通”C代码。

    int HandleFwrite(int num_params, char** params, char** output) {
      FILE* file;
      const char* file_index_string;
      const char* data;
      size_t data_len;
      size_t bytes_written;
    
      if (num_params != 2) {
        *output = PrintfToNewString("Error: fwrite takes 2 parameters.");
        return 1;
      }
    
      file_index_string = params[0];
      file = GetFileFromIndexString(file_index_string, NULL);
      data = params[1];
      data_len = strlen(data);
    
      if (!file) {
        *output = PrintfToNewString("Error: Unknown file handle %s.",
                                    file_index_string);
        return 2;
      }
    
      bytes_written = fwrite(data, 1, data_len, file);
    
      *output = PrintfToNewString("fwrite1%s1%d", file_index_string,
                                  bytes_written);
      return 0;
    }

    参考信息

    此处讨论的示例包含在目录中的SDK中 examples/demo/nacl_io_demo

    nacl_io库包含在SDK工具链中,不属于Pepper API的一部分。有关nacl_io接口的参考信息,请参阅位于的SDK目录中的头文件 include/nacl_io/nacl_io.h

    有关HTML5文件系统的更多信息,请阅读规范

    CC-By 3.0许可下提供的内容

  • 相关阅读:
    转 博客园 各种大牛合集
    系统学习qsort1 尤其partition
    转 大整数乘法 1 复杂度分析
    【转】如何设计一个LRU Cache?
    转微软大牛 13道链表操作
    框架设计之旅(1)--数据的分层
    框架设计之旅(2)--数据分层之实际应用
    DB2相关问题及解决方法:
    框架设计之旅--启航篇
    如何挑选水货诺基亚手机
  • 原文地址:https://www.cnblogs.com/SunkingYang/p/11049128.html
Copyright © 2011-2022 走看看