Symbian3/SDK/Source/GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6.dita
changeset 7 51a74ef9ed63
child 8 ae94777fff8f
equal deleted inserted replaced
6:43e37759235e 7:51a74ef9ed63
       
     1 <?xml version="1.0" encoding="utf-8"?>
       
     2 <!-- Copyright (c) 2007-2010 Nokia Corporation and/or its subsidiary(-ies) All rights reserved. -->
       
     3 <!-- This component and the accompanying materials are made available under the terms of the License 
       
     4 "Eclipse Public License v1.0" which accompanies this distribution, 
       
     5 and is available at the URL "http://www.eclipse.org/legal/epl-v10.html". -->
       
     6 <!-- Initial Contributors:
       
     7     Nokia Corporation - initial contribution.
       
     8 Contributors: 
       
     9 -->
       
    10 <!DOCTYPE concept
       
    11   PUBLIC "-//OASIS//DTD DITA Concept//EN" "concept.dtd">
       
    12 <concept id="GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6" xml:lang="en"><title>File Server
       
    13 Plugin Concepts</title><shortdesc>This topic describes the file server plug-in concepts.</shortdesc><prolog><metadata><keywords/></metadata></prolog><conbody>
       
    14 <p>File server plugins can issue direct file server requests, interpret and
       
    15 modify inbound messages and change file and metadata. A compression plugin
       
    16 may need to intercept file read or file write requests which are sent from
       
    17 the client to provide a seamless user experience. This operation requires
       
    18 the modification of the data, position and length arguments that are sent
       
    19 from the client to the file server. </p>
       
    20 <p>There are some limitations to the file server plugin framework: </p>
       
    21 <ul>
       
    22 <li id="GUID-1C02ECAE-A711-5E2A-8006-EC2D1BF5A859"><p>The file server plugin
       
    23 framework only operates on one client file at any time. However, a plugin
       
    24 itself can operate on any number of files during a single request from the
       
    25 client. </p> </li>
       
    26 <li id="GUID-F82C8E71-479B-5482-8234-C5AD2AD05A91"><p>The file server plugin
       
    27 framework does not enable the compression or encryption of whole volumes.
       
    28 If access to the whole media volume is needed use a <xref href="GUID-983F0ABD-470C-51C3-B6AE-1B1AA55AB4A2.dita">file
       
    29 server extension</xref> rather than a plugin. </p> </li>
       
    30 <li id="GUID-386C0911-30EF-56B0-BD3B-4BC97A7CEFA3"><p>File modification plugins
       
    31 cannot operate on demand paged executables. Demand paging does not use the
       
    32 file server, so the plugin framework cannot be used to encrypt/process the
       
    33 executable. </p> </li>
       
    34 </ul>
       
    35 <note> The improved framework will not prevent deadlock with existing plugins.
       
    36 Plugins that currently issue <xref href="GUID-E263C747-946F-35AA-9F1D-41833BD350FC.dita"><apiname>RFs</apiname></xref> requests must be migrated
       
    37 to the new APIs to prevent deadlock. Follow the guidelines within the <xref href="GUID-00764271-AD6B-5F41-AF72-843107EBF95F.dita">plugin implementation tutorial</xref></note>
       
    38 <ul>
       
    39 <li id="GUID-0A5ECCEA-CD70-528D-8880-463CA77D797B"><p> <xref href="GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6.dita#GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6/GUID-8B5B325D-D88C-55A7-9684-C2DCF81FCD79">Plugin type</xref>, </p> </li>
       
    40 <li id="GUID-40202D9E-C136-55BB-A5A1-DF64971B99D1"><p> <xref href="GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6.dita#GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6/GUID-C76B06C8-DEDC-57AC-A510-3DD1E232241A">Architecture</xref>, </p> </li>
       
    41 <li id="GUID-60C8A1F1-6BE6-59A3-8F33-BD7FBFF9FB59"><p> <xref href="GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6.dita#GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6/GUID-6234893D-A1C8-5870-9761-9EA2BD6909F0">Plugin order</xref>, </p> </li>
       
    42 <li id="GUID-20D4D10F-5E92-5FE3-A89C-DAF45E52EB0B"><p> <xref href="GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6.dita#GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6/GUID-DB21C0FD-46F8-5E4F-9288-69AE8609482B">Drive selection</xref>, </p> </li>
       
    43 <li id="GUID-91E1927C-3AA6-5594-8238-EA7B590278B2"><p> <xref href="GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6.dita#GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6/GUID-50F7CD3A-A051-5498-8886-B4501523FD1D">Interception of file server requests</xref>, </p> </li>
       
    44 <li id="GUID-59EB5503-3D02-5E2D-80A4-A20EA8364D81"><p> <xref href="GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6.dita#GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6/GUID-0B7B373D-41ED-5C91-ACC4-393A8669815A">Security</xref>. </p> </li>
       
    45 </ul>
       
    46 <section id="GUID-8B5B325D-D88C-55A7-9684-C2DCF81FCD79"><title>Plugin type</title> <p>There
       
    47 are two different types of file server plugins: </p> <ul>
       
    48 <li id="GUID-0FBE9E75-D164-5BCC-B00A-A5A76DBD200C"><p>Observer plugins - intercept
       
    49 requests but do not modify file data or associated meta data. </p> <p>Examples
       
    50 of observer plugins are those for virus scanning or logging. </p> </li>
       
    51 <li id="GUID-69708845-9C79-5C19-B758-AEF8F8A693E0"><p>Modifier plugins - intercept
       
    52 requests and modify the data or associated meta data of the target files or
       
    53 directories.. </p> <p>Examples of file modifier plugins are compression and
       
    54 encryption plugins. </p> </li>
       
    55 </ul> </section>
       
    56 <section id="GUID-C76B06C8-DEDC-57AC-A510-3DD1E232241A"><title>Architecture</title> <p>This
       
    57 section describes the structure of the plugin framework and the changes that
       
    58 have been made to the framework in v9.5: </p> <ul>
       
    59 <li id="GUID-399FE2E3-6576-5F98-83A8-70B9F77C65B7"><p> <xref href="GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6.dita#GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6/GUID-3D91570E-8939-557B-8E1E-3A3C5BD27A26">Threads and execution context</xref>, </p> </li>
       
    60 <li id="GUID-609612CB-E684-5BDA-88FC-16FFB71D70C2"><p> <xref href="GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6.dita#GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6/GUID-71DC7464-0EF0-5F78-816E-24F73F5FCA12">Exclusive access</xref>, </p> </li>
       
    61 <li id="GUID-665C36D1-DDD3-5DA4-86A3-574DFDC38AFF"><p> <xref href="GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6.dita#GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6/GUID-9C152BE3-9113-5A0C-8EE2-81ADD09BEAD2">Intercepting requests to the ROM drive</xref>, </p> </li>
       
    62 <li id="GUID-F06D0F56-40AA-5631-9686-BA955E8E263B"><p> <xref href="GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6.dita#GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6/GUID-AA3990F3-52AB-5B14-8ED4-50CCA824AF84">Preventing deadlock</xref>. </p> </li>
       
    63 </ul> <p>The diagram below shows how plugins fit into the File Server software
       
    64 stack. </p> <fig id="GUID-EF5AECEC-9CB0-54B0-B6D2-46266B5FF49E">
       
    65 <image href="GUID-9A4543B3-2A79-5604-AE11-5087507C6755_d0e265930_href.png" placement="inline"/>
       
    66 </fig> <p> <b>Note</b>: more than one plugin can be loaded into the file server
       
    67 at the same time. A plugin is not aware of other plugins. </p> <p id="GUID-3D91570E-8939-557B-8E1E-3A3C5BD27A26"><b> Threads and execution context</b> </p> <p>The
       
    68 Symbian platform File Server has multiple threads. There is a thread for each
       
    69 drive in use and a main thread that receives the requests from clients and
       
    70 sends them to the drive threads. Synchronous drives, however, do not have
       
    71 their own drive thread; requests for these are processed by the main thread.
       
    72 There is also a separate thread for processing session disconnect requests. </p> <p>Each
       
    73 plugin also has its own thread for processing requests. Requests are dispatched
       
    74 to the plugin thread associated with the request's drive before they are dispatched
       
    75 to the drive thread. This is discussed in more detail in <xref href="GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6.dita#GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6/GUID-50F7CD3A-A051-5498-8886-B4501523FD1D">interception of file server requests</xref>. </p> <p id="GUID-71DC7464-0EF0-5F78-816E-24F73F5FCA12"><b>Exclusive access</b> </p> <p>Previously,
       
    76 when a client application opens a file for exclusive write access, no other
       
    77 clients could access the file until the client closed its associated subsession.
       
    78 This also applied to plugins that needed to modify file data (as they are
       
    79 also clients of the file server). </p> <p>Symbian platform provides plugins
       
    80 that are able to perform operations on files and directories irrespective
       
    81 of the mode in which the file has been opened. </p> <p>Operations are now
       
    82 able to use the same file handle as the originating request (run in the same
       
    83 context as the original request) so files opened for exclusive access can
       
    84 still be written to by a plugin wishing to modify the file. </p> <p id="GUID-9C152BE3-9113-5A0C-8EE2-81ADD09BEAD2"><b>Intercepting ROM drive requests</b> </p> <p>Previously,
       
    85 plugins could not intercept any requests to the ROM drive (Z) however, there
       
    86 is a requirement to be able to intercept requests on this drive to enable
       
    87 secure-load and logging plugins. Requests to drive Z can now be intercepted
       
    88 by plugins. See the tutorial for <xref href="GUID-00764271-AD6B-5F41-AF72-843107EBF95F.dita#GUID-00764271-AD6B-5F41-AF72-843107EBF95F/GUID-89CF85BE-784F-5237-9F78-69D603B650C4">CFsPluginFactory</xref> for more details. </p> <p id="GUID-AA3990F3-52AB-5B14-8ED4-50CCA824AF84"><b>Preventing deadlock</b> </p> <p>The
       
    89 new framework allows a plugin to have direct access to file data without the
       
    90 need to issue new file server requests through the <xref href="GUID-BE0804F6-4375-3C8A-8C83-968F510466E0.dita"><apiname>RFile</apiname></xref>, <xref href="GUID-12AE154F-7741-38C0-ADFE-9784FCF5E516.dita"><apiname>RDir</apiname></xref> and <xref href="GUID-E263C747-946F-35AA-9F1D-41833BD350FC.dita"><apiname>RFs</apiname></xref> client
       
    91 APIs. In the pre-9.5 approach it was possible to reach deadlock if more than
       
    92 one plugin was present. </p> <p>The diagram below shows two plugins in the
       
    93 pre v9.5 framework. If both plugins issue new file server requests and if
       
    94 the plugins are not re-entrant safe this can lead to deadlock in the file
       
    95 server. </p> <fig id="GUID-01A69E82-BF01-520A-A8C5-927F1ED85E04">
       
    96 <title>                 File server deadlock               </title>
       
    97 <image href="GUID-9CC5E096-74FB-59AB-BAB9-A5486B961B7D_d0e266006_href.png" placement="inline"/>
       
    98 </fig> <p>The framework introduced in v9.5 prevents deadlock by allowing plugins
       
    99 to issue internal file server requests after intercepting a request by using
       
   100 the newly introduced <xref href="GUID-3C50CF63-9AF4-3F36-8B8F-3FBB613E1CAC.dita"><apiname>RFilePlugin</apiname></xref>, <xref href="GUID-2E871434-D08F-3275-AC55-260A9A78661A.dita"><apiname>RDirPlugin</apiname></xref> and <xref href="GUID-DE8D8017-6E9C-38CE-A023-98A53CDF7152.dita"><apiname>RFsPlugin</apiname></xref> APIs
       
   101 and not by using the <xref href="GUID-E263C747-946F-35AA-9F1D-41833BD350FC.dita"><apiname>RFs</apiname></xref>, <xref href="GUID-BE0804F6-4375-3C8A-8C83-968F510466E0.dita"><apiname>RFile</apiname></xref> and <xref href="GUID-12AE154F-7741-38C0-ADFE-9784FCF5E516.dita"><apiname>RDir</apiname></xref> APIs.
       
   102 Internally issued requests are only dispatched to plugins mounted below the
       
   103 issuing plugin and the appropriate drive thread. </p> <p>The sequence of events
       
   104 for a typical plugin intercepting a file read request is illustrated below: </p> <fig id="GUID-E366027F-3112-520F-A118-4C048102749E">
       
   105 <title>                 Read request intercepted by a plugin             
       
   106  </title>
       
   107 <image href="GUID-2ABCF233-7DCC-59E2-B075-81E148A1D2AB_d0e266044_href.png" placement="inline"/>
       
   108 </fig> <p>The classes <xref href="GUID-3C50CF63-9AF4-3F36-8B8F-3FBB613E1CAC.dita"><apiname>RFilePlugin</apiname></xref>, <xref href="GUID-2E871434-D08F-3275-AC55-260A9A78661A.dita"><apiname>RDirPlugin</apiname></xref> and <xref href="GUID-DE8D8017-6E9C-38CE-A023-98A53CDF7152.dita"><apiname>RFsPlugin</apiname></xref> have
       
   109 been introduced to facilitate plugins with direct access behaviour on file
       
   110 and directory requests. These classes are analogous to the client-side <xref href="GUID-BE0804F6-4375-3C8A-8C83-968F510466E0.dita"><apiname>RFile</apiname></xref>, <xref href="GUID-12AE154F-7741-38C0-ADFE-9784FCF5E516.dita"><apiname>RDir</apiname></xref> and <xref href="GUID-E263C747-946F-35AA-9F1D-41833BD350FC.dita"><apiname>RFs</apiname></xref> classes and have functions with similar or identical signitures. </p> <p>In
       
   111 order to perform requests on a file it is necessary to open a sub-session
       
   112 by calling either <xref href="GUID-EC8FDB25-3DD7-3F1C-9875-0FA9315AE9AC.dita"><apiname>AdoptFromClient()</apiname></xref> or <xref href="GUID-20D0D10F-3401-3F72-8AF6-DC35F6025DC2.dita"><apiname>Open()</apiname></xref>. <codeph>AdoptFromClient()</codeph> is
       
   113 used in order to open a sub-session with the file associated with the client’s
       
   114 request. Alternatively the <codeph>Open()</codeph> method can be used to open
       
   115 either a different file, or the file associated with the client’s request
       
   116 possibly with a different access mode. </p> <p>More than one file can be opened
       
   117 at any time by creating multiple instances of <xref href="GUID-3C50CF63-9AF4-3F36-8B8F-3FBB613E1CAC.dita"><apiname>RFilePlugin</apiname></xref>. </p> <p>The
       
   118 following example shows how to open many files from a plugin during a single
       
   119 request: </p> <codeblock id="GUID-AFCA6392-2414-591A-98C5-A9FC2C103755" xml:space="preserve">// Define the object
       
   120 RFilePlugin clientsFile(aRequest); 
       
   121 
       
   122 // Opens the file associated with the intercepted request
       
   123 Tint r = clientsFile.AdoptFromClient();
       
   124 User::LeaveIfError(r);
       
   125 TBuf&lt;20&gt; data;
       
   126 TInt64 pos = (Tint64)0;
       
   127 Tint length = 0;
       
   128 
       
   129 // Read the file
       
   130 r = clientsFile.Read(pos, data, length);
       
   131 User::LeaveIfError(r);
       
   132 
       
   133 // Open a second file
       
   134 RFilePlugin secondFile(aRequest);
       
   135 _LIT(KSecondName, ”D:\\myfile.txt”);
       
   136 r = secondFile.Open(KSecondName(), EFileRead);
       
   137 User::LeaveIfError(r);
       
   138 
       
   139 // Read from second file
       
   140 TBuf&lt;20&gt; data2;
       
   141 TInt64 pos2 = (Tint64)0;
       
   142 Tint length2 = 0;
       
   143 
       
   144 // Read the file
       
   145 r = secondFile.Read(pos2, data2, length2);
       
   146 User::LeaveIfError(r);
       
   147 
       
   148 // Close the files
       
   149 clientsFile.Close();
       
   150 secondFile.Close();</codeblock> <p><b>Issuing
       
   151 an internal file system request</b> </p> <p>An internal request can be marked
       
   152 as ‘Direct to Drive’. This allows requests that are generated by a plugin
       
   153 to be dispatched straight to the drive thread bypassing all other plugins
       
   154 which may be mounted below the plugin that issued the request. After being
       
   155 processed by the drive thread the request also bypasses the plugins between
       
   156 the drive thread and the plugin that the Direct to Drive request originated
       
   157 from. Once returned to the plugin that generated the request, the Direct to
       
   158 Drive request is complete and any other requests issued from the plugin are
       
   159 processed by plugins further down the plugin-stack in the normal manner. </p> <p>The
       
   160 last argument of the <xref href="GUID-3C50CF63-9AF4-3F36-8B8F-3FBB613E1CAC.dita"><apiname>RFilePlugin</apiname></xref> constructor of the classes <xref href="GUID-3C50CF63-9AF4-3F36-8B8F-3FBB613E1CAC.dita"><apiname>RFilePlugin</apiname></xref>, <xref href="GUID-DE8D8017-6E9C-38CE-A023-98A53CDF7152.dita"><apiname>RFsPlugin</apiname></xref> and <xref href="GUID-2E871434-D08F-3275-AC55-260A9A78661A.dita"><apiname>RDirPlugin</apiname></xref> is named <codeph>aDirectToDrive</codeph>. <codeph>aDirectToDrive</codeph> is
       
   161 a boolean value (<codeph>TBool</codeph>) to indicate that the request is Direct
       
   162 to Drive. The default value is <codeph>EFalse</codeph> indicating that the
       
   163 request is interceptable by plugins further down the plugin-stack. </p> </section>
       
   164 <section id="GUID-6234893D-A1C8-5870-9761-9EA2BD6909F0"><title>Plugin order</title> <p>The
       
   165 Plugin framework provides support for multiple plugins to be present and active.
       
   166 Plugins are arranged in a stack. Plugins intercept requests in the order they
       
   167 are arranged in the stack with the plugin at the top of the stack (at the
       
   168 smallest numerical absolute position) getting the first intercept. The order
       
   169 of plugins in the stack is therefore crucial to the correct operation of the
       
   170 file server when more than one plugin is active, especially when the plugins
       
   171 are modifier plugins (i.e when both modify the data or parameters of the requests). </p> <p>If
       
   172 two plugins are active and one of those is a virus scanner, for the virus
       
   173 scanner to operate correctly it must be the first plugin to intercept requests.
       
   174 This is so that the virus scanner can have first refusal to block any requests
       
   175 for files which it believes may not be safe for opening. If there is another
       
   176 plugin higher in the stack then this plugin could send Direct To Drive requests,
       
   177 for example, and would significantly reduce the virus scanning ability of
       
   178 the virus scanning plugin. </p> <p>Two mechanisms are provided that allow
       
   179 plugin authors to control the position of their plugins in the plugin stack
       
   180 these are Absolute position and Unique position. </p> <p id="GUID-5C258D67-C324-5FA4-894A-88532F925EFF"><b>Absolute position </b> </p> <p>Plugins
       
   181 can be inserted into the stack by specifying an absolute position at mount
       
   182 time. This absolute position is the index in the internal array of plugins
       
   183 in which the plugin should be mounted. The plugin at position 0 being the
       
   184 first plugin to be able to intercept requests. </p> <fig id="GUID-41EB2F58-407F-52C7-A40C-0E3858CF718B">
       
   185 <title>                 Plugin stack showing absolute positions          
       
   186     </title>
       
   187 <image href="GUID-64BDD1DA-6B93-5F45-8CBD-7DBAF92CC4C7_d0e266170_href.png" placement="inline"/>
       
   188 </fig> <p>The absolute position method is more appropriate for mounting plugins
       
   189 that operate regardless of their position in the plugin stack or when all
       
   190 of the plugins for a device are known and installed when manufactured. This
       
   191 method does not suit plugins that are added after manufacture where the dependencies
       
   192 of other available plugins is not known. If this is the case use the unique
       
   193 position method described below. </p> <p id="GUID-90FC1AD9-D709-5105-A445-0AA3D7BA85B7"><b>Unique position</b> </p> <p>Plugins
       
   194 can be ordered according to a unique position stored within the plugin. Unique
       
   195 position identifiers are defined by the manufacturer during the software validation/signing
       
   196 process. Unique positions are defined in the derived <xref href="GUID-8A3B2A79-05A6-3BD7-AEA9-02435476F45E.dita"><apiname>CFsPluginFactory</apiname></xref> class.
       
   197 See the description in <xref href="GUID-00764271-AD6B-5F41-AF72-843107EBF95F.dita#GUID-00764271-AD6B-5F41-AF72-843107EBF95F/GUID-89CF85BE-784F-5237-9F78-69D603B650C4">CFsPluginFactory</xref>. </p> <p>The position value specifies the category and position of the plugin: </p> <table id="GUID-22362455-13BE-5A26-8750-A94E79941EF3">
       
   198 <tgroup cols="2"><colspec colname="col0"/><colspec colname="col1"/>
       
   199 <tbody>
       
   200 <row>
       
   201 <entry><p> <b>plugin Type</b>  </p> </entry>
       
   202 <entry><p> <b>Unique Position Range</b>  </p> </entry>
       
   203 </row>
       
   204 <row>
       
   205 <entry><p>File Observers </p> </entry>
       
   206 <entry><p> <codeph>0x20000000 - 0x2FFFFFFF</codeph>  </p> </entry>
       
   207 </row>
       
   208 <row>
       
   209 <entry><p>File Modifiers </p> </entry>
       
   210 <entry><p> <codeph>0x40000000 - 0x4FFFFFFF</codeph>  </p> </entry>
       
   211 </row>
       
   212 </tbody>
       
   213 </tgroup>
       
   214 </table> <p>File Observers do not modify data so they are allocated a lower
       
   215 range of numbers placing them at the top of the plugin stack. File Modifiers
       
   216 modify the data stream so they are allocated a higher range placing them lower
       
   217 down the plugin stack. </p> <p> <b>Note</b>: a plugin has a unique position
       
   218 then do not specify an <xref href="GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6.dita#GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6/GUID-5C258D67-C324-5FA4-894A-88532F925EFF">absolute
       
   219 position</xref> when mounting it, otherwise the error <codeph>KErrNotSupported</codeph> is
       
   220 returned. </p> </section>
       
   221 <section id="GUID-DB21C0FD-46F8-5E4F-9288-69AE8609482B"><title>Drive selection</title> <p>A
       
   222 File Server Plugin can intercept requests for a specific drive or for all
       
   223 drives. A plugin that intercepts requests for all drives must filter requests
       
   224 that are not appropriate for some drives. Requests can be filtered within
       
   225 an overridden <xref href="GUID-00764271-AD6B-5F41-AF72-843107EBF95F.dita#GUID-00764271-AD6B-5F41-AF72-843107EBF95F/GUID-97427151-C6E4-5FE4-8197-0D7C58EDB29F">CFsPlugin::Deliver()</xref> function. </p> <p>There are two ways to specify a drive: </p> <ul>
       
   226 <li id="GUID-296E3A2E-5985-5E4B-96A2-D247D1FAA07C"><p>When the plugin is mounted.
       
   227 See <xref href="GUID-00764271-AD6B-5F41-AF72-843107EBF95F.dita#GUID-00764271-AD6B-5F41-AF72-843107EBF95F/GUID-BED54BD9-2F3F-588E-854B-C28745C8F30A">mounting
       
   228 a plugin</xref>. </p> </li>
       
   229 <li id="GUID-080CD9C3-2BEA-5209-974A-910606EBF22A"><p>At run-time through
       
   230 the use of <xref href="GUID-8A3B2A79-05A6-3BD7-AEA9-02435476F45E.dita#GUID-8A3B2A79-05A6-3BD7-AEA9-02435476F45E/GUID-45A67073-5EF4-3966-A2FD-555B56C89284"><apiname>CFsPluginFactory::iSupportedDrives</apiname></xref>. See the
       
   231 tutorial for <xref href="GUID-00764271-AD6B-5F41-AF72-843107EBF95F.dita#GUID-00764271-AD6B-5F41-AF72-843107EBF95F/GUID-89CF85BE-784F-5237-9F78-69D603B650C4">CFsPluginFactory</xref>. </p> </li>
       
   232 </ul> <p>If the drive is not specified then <xref href="GUID-E263C747-946F-35AA-9F1D-41833BD350FC.dita#GUID-E263C747-946F-35AA-9F1D-41833BD350FC/GUID-61640192-646E-33DA-B186-5EE63B07A998"><apiname>RFs::MountPlugin()</apiname></xref> attempts
       
   233 to mount the plugin for all drives. If this behaviour is not supported by
       
   234 the plugin <xref href="GUID-F89DA3F0-2A48-3F9B-8F08-29350E92D0E4.dita"><apiname>KErrNotSupported</apiname></xref> is returned. </p> </section>
       
   235 <section id="GUID-50F7CD3A-A051-5498-8886-B4501523FD1D"><title> Interception
       
   236 of file server requests</title> <p>After a file server request has been initialised
       
   237 by the main file server thread it can be intercepted by a plugin. There are
       
   238 two types of intercept: </p> <ul>
       
   239 <li id="GUID-288866F8-ABE5-5569-A70C-2C86B4F073B9"><p> <xref href="GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6.dita#GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6/GUID-05F613B8-FF66-54B6-8D49-2BF92914E54E">pre-operation intercepts</xref>, </p> </li>
       
   240 <li id="GUID-E876E576-1E94-5F06-8305-22D620A82B6F"><p> <xref href="GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6.dita#GUID-DEF3B8B3-5BD7-505B-93F9-A20CE00FFAE6/GUID-59FD1CED-5A32-5F6E-A256-821A2783D065">post-operation intercepts</xref>. </p> </li>
       
   241 </ul> <p>Plugins can register for pre-intercepts, for post-intercepts or for
       
   242 both pre and post-intercepts. </p> <p id="GUID-05F613B8-FF66-54B6-8D49-2BF92914E54E"><b>Pre-operation</b> </p> <p>Pre-operation
       
   243 intercepts occur before the drive associated with a request processes it.
       
   244 In a file write request for example, the pre-intercept operations occur before
       
   245 data has been written to the file. Requests are passed down the plugin-stack
       
   246 from the file server towards the drive thread. </p> <p>When the main file
       
   247 server thread has initialised a request, the request is dispatched to the
       
   248 highest plugin in the stack. This plugin must have been mounted on the requested
       
   249 drive and registered to pre-intercept this type of request. See <xref href="GUID-00764271-AD6B-5F41-AF72-843107EBF95F.dita#GUID-00764271-AD6B-5F41-AF72-843107EBF95F/GUID-BED54BD9-2F3F-588E-854B-C28745C8F30A">mounting a plugin</xref>. The request is dispatched by calling the plugin's <xref href="GUID-BC0DB991-EF52-3344-8E6A-F8060B75A189.dita#GUID-BC0DB991-EF52-3344-8E6A-F8060B75A189/GUID-2EACA8A8-D569-3D6A-9383-451587A65839"><apiname>CFsPlugin::Deliver()</apiname></xref> function. </p> <p>The <codeph>Deliver()</codeph> function runs in the context of the previous calling thread,
       
   250 this can be the main file server thread or a plugin thread. Override <codeph>CFsPlugin::Deliver()</codeph> to
       
   251 filter the request. If the <codeph>Deliver()</codeph> function has not been
       
   252 overridden then the request is dispatched for asynchronous processing by calling
       
   253 the base class <codeph>Deliver()</codeph>. See the <xref href="GUID-00764271-AD6B-5F41-AF72-843107EBF95F.dita#GUID-00764271-AD6B-5F41-AF72-843107EBF95F/GUID-97427151-C6E4-5FE4-8197-0D7C58EDB29F">CFsPlugin::Deliver()</xref> tutorial section. </p> <p id="GUID-59FD1CED-5A32-5F6E-A256-821A2783D065"><b>Post operation</b> </p> <p>Post-operation
       
   254 intercepts occur after the drive associated with a request has processed it.
       
   255 In a file write request for example, the post-intercept occurs after data
       
   256 has been written to the file. Requests are passed from the drive thread back
       
   257 up the stack towards the client. </p> <p>When the drive thread has finished
       
   258 processing a request it dispatches it to the plugin lowest in the stack by
       
   259 calling the plugin's <xref href="GUID-C6F20230-3D6C-3392-B040-CF627534B930.dita"><apiname>Deliver()</apiname></xref> function. </p> <p><b> Filtering requests internally</b> </p> <p>The <xref href="GUID-F1B37142-1EEF-3777-82B1-303982B888EC.dita#GUID-F1B37142-1EEF-3777-82B1-303982B888EC/GUID-8EBEAD17-B03C-3DBA-9A47-0F7DB07785F9"><apiname>CFSPlugin::Deliver()</apiname></xref> function
       
   260 filters the request and decides what kind of action is neccessary in terms
       
   261 of the flow of the request through the plugin stack: </p> <ul>
       
   262 <li id="GUID-3E8CAD7B-BE13-531E-A387-432F4CD463C9"><p> <xref href="GUID-1E025D93-3D66-3E88-830D-CBB3A471A777.dita"><apiname>KPluginMessageForward</apiname></xref> is
       
   263 returned if the intercept is pre-operation. The request is passed to the next
       
   264 plugin down the stack or to the drive thread if there are no more plugins. </p> </li>
       
   265 <li id="GUID-1FFEFFF4-3D5F-590F-8884-CA27B2B5B916"><p> <xref href="GUID-81C5F6A1-3FCA-33E5-99C6-7901D41BCBDE.dita"><apiname>KPluginMessageComplete</apiname></xref> is
       
   266 returned if the intercept is post-operation. The request is passed to the
       
   267 next plugin up the stack or if there are no more plugins to process the request
       
   268 it is passed to the main file server thread. </p> </li>
       
   269 </ul> <p>If the request requires processing by the plugin then the plugin's <codeph>Deliver()</codeph> function
       
   270 calls the base class <codeph>Deliver()</codeph> function and the request is
       
   271 dispatched to the plugin's thread for asynchronous processing. </p> <p>Asynchronous
       
   272 processing is carried out in the plugin's <xref href="GUID-8EF10689-68B7-391B-AD5C-4F51780165FF.dita"><apiname>DoRequestL()</apiname></xref> function.
       
   273 A plugin can only have a single <codeph>DoRequestL()</codeph> function which
       
   274 must handle both pre and post-intercepts. Plugin authors can use the <xref href="GUID-06E787C2-FAC1-36D2-9C64-11BDA1B656F1.dita"><apiname>IsPostOperation()</apiname></xref> function
       
   275 of the utility class, <xref href="GUID-A814151C-8AEC-3E16-8691-33174B64E36F.dita"><apiname>TFsPluginRequest</apiname></xref> to indicate whether
       
   276 the <codeph>DoRequestL()</codeph> is processing a request as a pre-intercept
       
   277 or post-intercept. See the description of <xref href="GUID-00764271-AD6B-5F41-AF72-843107EBF95F.dita#GUID-00764271-AD6B-5F41-AF72-843107EBF95F/GUID-14773530-7C15-52E2-A542-72A0B2163461">TFsPluginRequest</xref>. </p> <p>Once the asynchronous processing is complete the <codeph>DoRequestL()</codeph> function
       
   278 returns <codeph>KErrNone</codeph> and the request is passed to the next plugin
       
   279 down the stack by calling its <xref href="GUID-C6F20230-3D6C-3392-B040-CF627534B930.dita"><apiname>Deliver()</apiname></xref> function. If there
       
   280 are no lower plugins then the request is passed to the appropriate drive thread
       
   281 for processing. </p> <p>If the plugin intercepts a request in pre-operation
       
   282 and wants to complete the request on behalf of the client then the plugin
       
   283 can return <xref href="GUID-DCECEF73-9C33-3C14-951D-E75D89B21FBA.dita"><apiname>KErrCompletion</apiname></xref> to indicate that the request
       
   284 has been completed and that the request is now in post operation mode. The
       
   285 flow will then proceed to any previous plugins if mounted or directly back
       
   286 to the client otherwise. <xref href="GUID-DCECEF73-9C33-3C14-951D-E75D89B21FBA.dita"><apiname>KErrCompletion</apiname></xref> prevents any further
       
   287 plugins further down the stack from intercepting the request. </p> <p>When
       
   288 a plugin intercepts file read or file write and does an early completion (i.e.
       
   289 returns <xref href="GUID-DCECEF73-9C33-3C14-951D-E75D89B21FBA.dita"><apiname>KErrCompletion</apiname></xref> in pre-intercept) then the plugin
       
   290 author should call <xref href="GUID-A814151C-8AEC-3E16-8691-33174B64E36F.dita#GUID-A814151C-8AEC-3E16-8691-33174B64E36F/GUID-149E1448-63AA-3F08-A3A2-606D240A8927"><apiname>TFsPluginRequest::SetSharePos()</apiname></xref> to allow
       
   291 share position to be updated after early read/write completion. </p> </section>
       
   292 <section id="GUID-0B7B373D-41ED-5C91-ACC4-393A8669815A"><title>Security</title> <p>File
       
   293 server plugins are implemented as libraries that are loaded into the file
       
   294 server process at runtime. Therefore, plugins must have the same <xref href="GUID-4BFEDD79-9502-526A-BA7B-97550A6F0601.dita">platform
       
   295 security</xref> capabilities as the file server process, these are <xref href="GUID-2A022229-C333-3B0A-99A5-13CA0710025D.dita"><apiname>TCB</apiname></xref>, <xref href="GUID-E5C21B79-529B-397E-8A22-63612CA52869.dita"><apiname>ProtServ</apiname></xref>, <xref href="GUID-8DC76E7B-9EB3-3848-AD8D-3D519388A504.dita"><apiname>DiskAdmin</apiname></xref>, <xref href="GUID-ECCA7246-B2BA-3261-95C9-9E72C6EC51D4.dita"><apiname>AllFiles</apiname></xref>, <xref href="GUID-93881606-AA56-385F-A958-3957142BEFE3.dita"><apiname>PowerMgmt</apiname></xref> and <xref href="GUID-616F0C5B-D2C1-39D8-9BFC-53A2AEC7C850.dita"><apiname>CommDD</apiname></xref>. </p> <p>Any
       
   296 user side process that wishes to load and mount plugins must have the <codeph>DiskAdmin</codeph> capability. </p> </section>
       
   297 </conbody></concept>