home *** CD-ROM | disk | FTP | other *** search
/ ftp.parl.clemson.edu / 2015-02-07.ftp.parl.clemson.edu.tar / ftp.parl.clemson.edu / pub / pvfs2 / orangefs-2.8.3-20110323.tar.gz / orangefs-2.8.3-20110323.tar / orangefs / src / client / sysint / sys-flush.sm < prev    next >
Text File  |  2008-11-19  |  7KB  |  276 lines

  1. /* 
  2.  * (C) 2003 Clemson University and The University of Chicago 
  3.  *
  4.  * See COPYING in top-level directory.
  5.  */
  6.  
  7. /** \file
  8.  *  \ingroup sysint
  9.  *
  10.  *  PVFS2 system interface routines for flushing data to disk on servers.
  11.  */
  12.  
  13. #include <string.h>
  14. #include <assert.h>
  15.  
  16. #include "client-state-machine.h"
  17. #include "pvfs2-debug.h"
  18. #include "job.h"
  19. #include "gossip.h"
  20. #include "str-utils.h"
  21. #include "pint-cached-config.h"
  22. #include "PINT-reqproto-encode.h"
  23. #include "pint-util.h"
  24. #include "pvfs2-internal.h"
  25.  
  26. extern job_context_id pint_client_sm_context;
  27.  
  28. %%
  29.  
  30. machine pvfs2_client_flush_sm
  31. {
  32.     state flush_getattr
  33.     {
  34.         jump pvfs2_client_getattr_sm;
  35.         success => flush_datafile_setup_msgpairarray;
  36.         default => cleanup;
  37.     }
  38.  
  39.     state flush_datafile_setup_msgpairarray
  40.     {
  41.         run flush_datafile_setup_msgpairarray;
  42.         success => flush_datafile_xfer_msgpairarray;
  43.         default => cleanup;
  44.     }
  45.  
  46.     state flush_datafile_xfer_msgpairarray
  47.     {
  48.         jump pvfs2_msgpairarray_sm;
  49.         success => cleanup;
  50.         default => flush_datafile_flush_failure;
  51.     }
  52.  
  53.     state flush_datafile_flush_failure
  54.     {
  55.         run flush_datafile_flush_failure;
  56.         default => cleanup;
  57.     }
  58.     
  59.     state cleanup
  60.     {
  61.         run flush_cleanup;
  62.         default => terminate;
  63.     }
  64. }
  65.  
  66. %%
  67.  
  68. /** Initiate flushing of file data to storage on servers.
  69.  */
  70. PVFS_error PVFS_isys_flush(
  71.     PVFS_object_ref ref,
  72.     const PVFS_credentials *credentials,
  73.     PVFS_sys_op_id *op_id,
  74.     PVFS_hint hints,
  75.     void *user_ptr)
  76. {
  77.     PVFS_error ret = -PVFS_EINVAL;
  78.     PINT_smcb *smcb = NULL;
  79.     PINT_client_sm *sm_p = NULL;
  80.  
  81.     gossip_debug(GOSSIP_CLIENT_DEBUG, "PVFS_isys_flush entered\n");
  82.  
  83.     if ((ref.fs_id == PVFS_FS_ID_NULL) ||
  84.         (ref.handle == PVFS_HANDLE_NULL))
  85.     {
  86.         gossip_err("Invalid handle/fs_id specified\n");
  87.         return ret;
  88.     }
  89.  
  90.     PINT_smcb_alloc(&smcb, PVFS_SYS_FLUSH,
  91.              sizeof(struct PINT_client_sm),
  92.              client_op_state_get_machine,
  93.              client_state_machine_terminate,
  94.              pint_client_sm_context);
  95.     if (!smcb)
  96.     {
  97.         return -PVFS_ENOMEM;
  98.     }
  99.     sm_p = PINT_sm_frame(smcb, PINT_FRAME_CURRENT);
  100.  
  101.     PINT_init_msgarray_params(sm_p, ref.fs_id);
  102.     PINT_init_sysint_credentials(sm_p->cred_p, credentials);
  103.     sm_p->object_ref = ref;
  104.     PVFS_hint_copy(hints, &sm_p->hints);
  105.     PVFS_hint_add(&sm_p->hints, PVFS_HINT_HANDLE_NAME, sizeof(PVFS_handle), &ref.handle);
  106.  
  107.     /* NOTE: This state machine previously multiplied the default job timeout
  108.      * by five to allow for potentially long sync delays.  We instead now set
  109.      * the default client BMI timeout higher for all operations: if a sync can 
  110.      * go slow then so can any other arbitrary operation queued behind it. -PHC
  111.      */
  112.  
  113.     PINT_SM_GETATTR_STATE_FILL(
  114.         sm_p->getattr,
  115.         ref,
  116.         PVFS_ATTR_META_ALL|PVFS_ATTR_COMMON_TYPE, 
  117.         PVFS_TYPE_METAFILE,
  118.         0);
  119.  
  120.     return PINT_client_state_machine_post(
  121.         smcb,  op_id, user_ptr);
  122. }
  123.  
  124. /** Flush file data to storage on servers.
  125.  */
  126. PVFS_error PVFS_sys_flush(
  127.     PVFS_object_ref ref,
  128.     const PVFS_credentials *credentials,
  129.     PVFS_hint hints)
  130. {
  131.     PVFS_error ret = -PVFS_EINVAL, error = 0;
  132.     PVFS_sys_op_id op_id;
  133.  
  134.     gossip_debug(GOSSIP_CLIENT_DEBUG, "PVFS_sys_flush entered\n");
  135.  
  136.     ret = PVFS_isys_flush(ref, credentials, &op_id, hints, NULL);
  137.     if (ret)
  138.     {
  139.         PVFS_perror_gossip("PVFS_isys_flush call", ret);
  140.         error = ret;
  141.     }
  142.     else
  143.     {
  144.         ret = PVFS_sys_wait(op_id, "flush", &error);
  145.         if (ret)
  146.         {
  147.             PVFS_perror_gossip("PVFS_sys_wait call", ret);
  148.             error = ret;
  149.         }
  150.     }
  151.  
  152.     PINT_sys_release(op_id);
  153.     return error;
  154. }
  155.  
  156. static int flush_datafile_setup_msgpairarray(
  157.         struct PINT_smcb *smcb, job_status_s *js_p)
  158. {
  159.     struct PINT_client_sm *sm_p = PINT_sm_frame(smcb, PINT_FRAME_CURRENT);
  160.     int ret = -PVFS_EINVAL, i = 0;
  161.     PVFS_object_attr *attr = NULL;
  162.     PINT_sm_msgpair_state *msg_p = NULL;
  163.  
  164.     gossip_debug(GOSSIP_CLIENT_DEBUG, "(%p) flush state: "
  165.                  "datafile_setup_msgpairarray\n", sm_p);
  166.  
  167.     js_p->error_code = 0;
  168.  
  169.     attr = &sm_p->getattr.attr;
  170.     assert(attr);
  171.     assert(attr->mask & PVFS_ATTR_META_DFILES);
  172.     assert(attr->u.meta.dfile_count > 0);
  173.  
  174.     ret = PINT_msgpairarray_init(&sm_p->msgarray_op, (attr->u.meta.dfile_count + 1));
  175.     if(ret != 0)
  176.     {
  177.         gossip_err("Failed to initialize %d msgpairs\n",
  178.                    (attr->u.meta.dfile_count + 1));
  179.         js_p->error_code = ret;
  180.         return SM_ACTION_COMPLETE;
  181.     }
  182.  
  183.     /* datafile count + 1 metafile */
  184.     foreach_msgpair(&sm_p->msgarray_op, msg_p, i)
  185.     {
  186.         if (i < attr->u.meta.dfile_count)
  187.         {
  188.             gossip_debug(GOSSIP_CLIENT_DEBUG,
  189.                          "  datafile_flush: flushing handle %llu\n",
  190.                          llu(attr->u.meta.dfile_array[i]));
  191.  
  192.             PINT_SERVREQ_FLUSH_FILL(msg_p->req,
  193.                                     *sm_p->cred_p,
  194.                                     sm_p->object_ref.fs_id,
  195.                                     attr->u.meta.dfile_array[i],
  196.                                     sm_p->hints);
  197.  
  198.             msg_p->fs_id = sm_p->object_ref.fs_id;
  199.             msg_p->handle = attr->u.meta.dfile_array[i];
  200.             msg_p->retry_flag = PVFS_MSGPAIR_RETRY;
  201.             msg_p->comp_fn = NULL;
  202.         }
  203.         else
  204.         {
  205.             assert(i == (sm_p->msgarray_op.count - 1));
  206.  
  207.             gossip_debug(GOSSIP_CLIENT_DEBUG,
  208.                          "  metafile_flush: flushing handle %llu\n",
  209.                          llu(sm_p->object_ref.handle));
  210.  
  211.             PINT_SERVREQ_FLUSH_FILL(msg_p->req,
  212.                                     *sm_p->cred_p,
  213.                                     sm_p->object_ref.fs_id,
  214.                                     sm_p->object_ref.handle,
  215.                                     sm_p->hints);
  216.  
  217.             msg_p->fs_id = sm_p->object_ref.fs_id;
  218.             msg_p->handle = sm_p->object_ref.handle;
  219.             msg_p->retry_flag = PVFS_MSGPAIR_RETRY;
  220.             msg_p->comp_fn = NULL;
  221.         }
  222.     }
  223.  
  224.     ret = PINT_serv_msgpairarray_resolve_addrs(&sm_p->msgarray_op);
  225.     if (ret)
  226.     {
  227.         gossip_err("Error: failed to resolve server addresses.\n");
  228.         js_p->error_code = ret;
  229.     }
  230.  
  231.     PINT_sm_push_frame(smcb, 0, &sm_p->msgarray_op);
  232.     return SM_ACTION_COMPLETE;
  233. }
  234.  
  235. static int flush_datafile_flush_failure(
  236.         struct PINT_smcb *smcb, job_status_s *js_p)
  237. {
  238.     struct PINT_client_sm *sm_p = PINT_sm_frame(smcb, PINT_FRAME_CURRENT);
  239.     gossip_debug(GOSSIP_CLIENT_DEBUG,
  240.                  "(%p) flush state: datafile_flush_failure\n",
  241.                  sm_p);
  242.     return SM_ACTION_COMPLETE;
  243. }
  244.  
  245. static int flush_cleanup(
  246.         struct PINT_smcb *smcb, job_status_s *js_p)
  247. {
  248.     struct PINT_client_sm *sm_p = PINT_sm_frame(smcb, PINT_FRAME_CURRENT);
  249.     gossip_debug(GOSSIP_CLIENT_DEBUG,
  250.                  "(%p) flush state: flush_cleanup\n", sm_p);
  251.  
  252.     sm_p->error_code = js_p->error_code;
  253.  
  254.     if(sm_p->error_code != 0)
  255.     {
  256.         PINT_acache_invalidate(sm_p->object_ref);
  257.     }
  258.  
  259.     PINT_SM_GETATTR_STATE_CLEAR(sm_p->getattr);
  260.  
  261.     PINT_msgpairarray_destroy(&sm_p->msgarray_op);
  262.  
  263.     PINT_SET_OP_COMPLETE;
  264.     return SM_ACTION_TERMINATE;
  265. }
  266.  
  267. /*
  268.  * Local variables:
  269.  *  mode: c
  270.  *  c-indent-level: 4
  271.  *  c-basic-offset: 4
  272.  * End:
  273.  *
  274.  * vim: ft=c ts=8 sts=4 sw=4 expandtab
  275.  */
  276.