1. 02 5月, 2013 18 次提交
    • A
      libceph: combine initializing and setting osd data · a4ce40a9
      Alex Elder 提交于
      This ends up being a rather large patch but what it's doing is
      somewhat straightforward.
      
      Basically, this is replacing two calls with one.  The first of the
      two calls is initializing a struct ceph_osd_data with data (either a
      page array, a page list, or a bio list); the second is setting an
      osd request op so it associates that data with one of the op's
      parameters.  In place of those two will be a single function that
      initializes the op directly.
      
      That means we sort of fan out a set of the needed functions:
          - extent ops with pages data
          - extent ops with pagelist data
          - extent ops with bio list data
      and
          - class ops with page data for receiving a response
      
      We also have define another one, but it's only used internally:
          - class ops with pagelist data for request parameters
      
      Note that we *still* haven't gotten rid of the osd request's
      r_data_in and r_data_out fields.  All the osd ops refer to them for
      their data.  For now, these data fields are pointers assigned to the
      appropriate r_data_* field when these new functions are called.
      Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      a4ce40a9
    • A
      rbd: rearrange some code for consistency · 2169238d
      Alex Elder 提交于
      This patch just trivially moves around some code for consistency.
      
      In preparation for initializing osd request data fields in
      ceph_osdc_build_request(), I wanted to verify that rbd did in fact
      call that immediately before it called ceph_osdc_start_request().
      It was true (although image requests are built in a group and then
      started as a group).  But I made the changes here just to make
      it more obvious, by making all of the calls follow a common
      sequence:
      	osd_req_op_<optype>_init();
      	ceph_osd_data_<type>_init()
      	osd_req_op_<optype>_<datafield>()
      	rbd_osd_req_format()
      	...
      	ret = rbd_obj_request_submit()
      
      I moved the initialization of the callback for image object requests
      into rbd_img_request_fill_bio(), again, for consistency.  To avoid
      a forward reference, I moved the definition of rbd_img_obj_callback()
      up in the file.
      Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      2169238d
    • A
      rbd: separate initialization of osd data · 44cd188d
      Alex Elder 提交于
      The osd data for a request is currently initialized inside
      rbd_osd_req_create(), but that assumes an object request's data
      belongs in the osd request's data in or data out field.
      
      There are only three places where requests with data are set up, and
      it turns out it's easier to call just the osd data init routines
      directly there rather than handling it in rbd_osd_req_create().
      
      (The real motivation here is moving toward getting rid of the
      osd request in and out data fields.)
      Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      44cd188d
    • A
      rbd: don't set data in rbd_osd_req_format_op() · 2fa12320
      Alex Elder 提交于
      Currently an object request has its osd request's data field set in
      rbd_osd_req_format_op().  That assumes a single osd op per object
      request, and that won't be the case for long.
      
      Move the code that sets this out and into the caller.
      
      Rename rbd_osd_req_format_op() to be just rbd_osd_req_format(),
      removing the notion that it's doing anything op-specific.
      
      This and the next patch resolve:
          http://tracker.ceph.com/issues/4658Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      2fa12320
    • A
      libceph: specify osd op by index in request · c99d2d4a
      Alex Elder 提交于
      An osd request now holds all of its source op structures, and every
      place that initializes one of these is in fact initializing one
      of the entries in the the osd request's array.
      
      So rather than supplying the address of the op to initialize, have
      caller specify the osd request and an indication of which op it
      would like to initialize.  This better hides the details the
      op structure (and faciltates moving the data pointers they use).
      
      Since osd_req_op_init() is a common routine, and it's not used
      outside the osd client code, give it static scope.  Also make
      it return the address of the specified op (so all the other
      init routines don't have to repeat that code).
      Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      c99d2d4a
    • A
      libceph: add data pointers in osd op structures · 8c042b0d
      Alex Elder 提交于
      An extent type osd operation currently implies that there will
      be corresponding data supplied in the data portion of the request
      (for write) or response (for read) message.  Similarly, an osd class
      method operation implies a data item will be supplied to receive
      the response data from the operation.
      
      Add a ceph_osd_data pointer to each of those structures, and assign
      it to point to eithre the incoming or the outgoing data structure in
      the osd message.  The data is not always available when an op is
      initially set up, so add two new functions to allow setting them
      after the op has been initialized.
      
      Begin to make use of the data item pointer available in the osd
      operation rather than the request data in or out structure in
      places where it's convenient.  Add some assertions to verify
      pointers are always set the way they're expected to be.
      
      This is a sort of stepping stone toward really moving the data
      into the osd request ops, to allow for some validation before
      making that jump.
      
      This is the first in a series of patches that resolve:
          http://tracker.ceph.com/issues/4657Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      8c042b0d
    • A
      libceph: keep source rather than message osd op array · 79528734
      Alex Elder 提交于
      An osd request keeps a pointer to the osd operations (ops) array
      that it builds in its request message.
      
      In order to allow each op in the array to have its own distinct
      data, we will need to keep track of each op's data, and that
      information does not go over the wire.
      
      As long as we're tracking the data we might as well just track the
      entire (source) op definition for each of the ops.  And if we're
      doing that, we'll have no more need to keep a pointer to the
      wire-encoded version.
      
      This patch makes the array of source ops be kept with the osd
      request structure, and uses that instead of the version encoded in
      the message in places where that was previously used.  The array
      will be embedded in the request structure, and the maximum number of
      ops we ever actually use is currently 2.  So reduce CEPH_OSD_MAX_OP
      to 2 to reduce the size of the structure.
      
      The result of doing this sort of ripples back up, and as a result
      various function parameters and local variables become unnecessary.
      
      Make r_num_ops be unsigned, and move the definition of struct
      ceph_osd_req_op earlier to ensure it's defined where needed.
      
      It does not yet add per-op data, that's coming soon.
      
      This resolves:
          http://tracker.ceph.com/issues/4656Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      79528734
    • A
      rbd: define rbd_osd_req_format_op() · 430c28c3
      Alex Elder 提交于
      Define rbd_osd_req_format_op(), which encapsulates formatting
      an osd op into an object request's osd request message.  Only
      one op is supported right now.
      
      Stop calling ceph_osdc_build_request() in rbd_osd_req_create().
      Instead, call rbd_osd_req_format_op() in each of the callers of
      rbd_osd_req_create().
      
      This is to prepare for the next patch, in which the source ops for
      an osd request will be held in the osd request itself.  Because of
      that, we won't have the source op to work with until after the
      request is created, so we can't format the op until then.
      
      This an the next patch resolve:
          http://tracker.ceph.com/issues/4656Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      430c28c3
    • A
      libceph: define osd data initialization helpers · 43bfe5de
      Alex Elder 提交于
      Define and use functions that encapsulate the initializion of a
      ceph_osd_data structure.
      Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      43bfe5de
    • A
      rbd: define inbound data size for method ops · 6010a451
      Alex Elder 提交于
      When rbd creates an object request containing an object method call
      operation it is passing 0 for the size.  I originally thought this
      was because the length was not needed for method calls, but I think
      it really should be supplied, to describe how much space is
      available to receive response data.  So provide the supplied length.
      
      This resolves:
          http://tracker.ceph.com/issues/4659Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      6010a451
    • A
      libceph: record length of bio list with bio · fdce58cc
      Alex Elder 提交于
      When assigning a bio pointer to an osd request, we don't have an
      efficient way of knowing the total length bytes in the bio list.
      That information is available at the point it's set up by the rbd
      code, so record it with the osd data when it's set.
      
      This and the next patch are related to maintaining the length of a
      message's data independent of the message header, as described here:
          http://tracker.ceph.com/issues/4589Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      fdce58cc
    • A
      libceph: define source request op functions · 33803f33
      Alex Elder 提交于
      The rbd code has a function that allocates and populates a
      ceph_osd_req_op structure (the in-core version of an osd request
      operation).  When reviewed, Josh suggested two things: that the
      big varargs function might be better split into type-specific
      functions; and that this functionality really belongs in the osd
      client rather than rbd.
      
      This patch implements both of Josh's suggestions.  It breaks
      up the rbd function into separate functions and defines them
      in the osd client module as exported interfaces.  Unlike the
      rbd version, however, the functions don't allocate an osd_req_op
      structure; they are provided the address of one and that is
      initialized instead.
      
      The rbd function has been eliminated and calls to it have been
      replaced by calls to the new routines.  The rbd code now now use a
      stack (struct) variable to hold the op rather than allocating and
      freeing it each time.
      
      For now only the capabilities used by rbd are implemented.
      Implementing all the other osd op types, and making the rest of the
      code use it will be done separately, in the next few patches.
      
      Note that only the extent, cls, and watch portions of the
      ceph_osd_req_op structure are currently used.  Delete the others
      (xattr, pgls, and snap) from its definition so nobody thinks it's
      actually implemented or needed.  We can add it back again later
      if needed, when we know it's been tested.
      
      This (and a few follow-on patches) resolves:
          http://tracker.ceph.com/issues/3861Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      33803f33
    • A
      ceph: move max constant definitions · adfe695a
      Alex Elder 提交于
      Move some definitions for max integer values out of the rbd code and
      into the more central "decode.h" header file.  These really belong
      in a Linux (or libc) header somewhere, but I haven't gotten around
      to proposing that yet.
      
      This is in preparation for moving some code out of rbd.c and into
      the osd client.
      Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      adfe695a
    • A
      libceph: let osd ops determine request data length · 175face2
      Alex Elder 提交于
      The length of outgoing data in an osd request is dependent on the
      osd ops that are embedded in that request.  Each op is encoded into
      a request message using osd_req_encode_op(), so that should be used
      to determine the amount of outgoing data implied by the op as it
      is encoded.
      
      Have osd_req_encode_op() return the number of bytes of outgoing data
      implied by the op being encoded, and accumulate and use that in
      ceph_osdc_build_request().
      
      As a result, ceph_osdc_build_request() no longer requires its "len"
      parameter, so get rid of it.
      
      Using the sum of the op lengths rather than the length provided is
      a valid change because:
          - The only callers of osd ceph_osdc_build_request() are
            rbd and the osd client (in ceph_osdc_new_request() on
            behalf of the file system).
          - When rbd calls it, the length provided is only non-zero for
            write requests, and in that case the single op has the
            same length value as what was passed here.
          - When called from ceph_osdc_new_request(), (it's not all that
            easy to see, but) the length passed is also always the same
            as the extent length encoded in its (single) write op if
            present.
      
      This resolves:
          http://tracker.ceph.com/issues/4406Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      175face2
    • A
      libceph: record byte count not page count · e0c59487
      Alex Elder 提交于
      Record the byte count for an osd request rather than the page count.
      The number of pages can always be derived from the byte count (and
      alignment/offset) but the reverse is not true.
      Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      e0c59487
    • A
      libceph: separate read and write data · 0fff87ec
      Alex Elder 提交于
      An osd request defines information about where data to be read
      should be placed as well as where data to write comes from.
      Currently these are represented by common fields.
      
      Keep information about data for writing separate from data to be
      read by splitting these into data_in and data_out fields.
      
      This is the key patch in this whole series, in that it actually
      identifies which osd requests generate outgoing data and which
      generate incoming data.  It's less obvious (currently) that an osd
      CALL op generates both outgoing and incoming data; that's the focus
      of some upcoming work.
      
      This resolves:
          http://tracker.ceph.com/issues/4127Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      0fff87ec
    • A
      libceph: distinguish page and bio requests · 2ac2b7a6
      Alex Elder 提交于
      An osd request uses either pages or a bio list for its data.  Use a
      union to record information about the two, and add a data type
      tag to select between them.
      Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      2ac2b7a6
    • A
      libceph: separate osd request data info · 2794a82a
      Alex Elder 提交于
      Pull the fields in an osd request structure that define the data for
      the request out into a separate structure.
      Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      2794a82a
  2. 18 4月, 2013 1 次提交
  3. 30 3月, 2013 1 次提交
    • A
      rbd: don't zero-fill non-image object requests · 6e2a4505
      Alex Elder 提交于
      A result of ENOENT from a read request for an object that's part of
      an rbd image indicates that there is a hole in that portion of the
      image.  Similarly, a short read for such an object indicates that
      the remainder of the read should be interpreted a full read with
      zeros filling out the end of the request.
      
      This behavior is not correct for objects that are not backing rbd
      image data.  Currently rbd_img_obj_request_callback() assumes it
      should be done for all objects.
      
      Change rbd_img_obj_request_callback() so it only does this zeroing
      for image objects.  Encapsulate that special handling in its own
      function.  Add an assertion that the image object request is a bio
      request, since we assume that (and we currently don't support any
      other types).
      
      This resolves a problem identified here:
          http://tracker.ceph.com/issues/4559
      
      The regression was introduced by bf0d5f50.
      Reported-by: NDan van der Ster <dan@vanderster.com>
      Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-off-by: NSage Weil <sage@inktank.com>
      6e2a4505
  4. 27 2月, 2013 3 次提交
    • S
      libceph: update osd request/reply encoding · 1b83bef2
      Sage Weil 提交于
      Use the new version of the encoding for osd requests and replies.  In the
      process, update the way we are tracking request ops and reply lengths and
      results in the struct ceph_osd_request.  Update the rbd and fs/ceph users
      appropriately.
      
      The main changes are:
       - we keep pointers into the request memory for fields we need to update
         each time the request is sent out over the wire
       - we keep information about the result in an array in the request struct
         where the users can easily get at it.
      Signed-off-by: NSage Weil <sage@inktank.com>
      Reviewed-by: NAlex Elder <elder@inktank.com>
      1b83bef2
    • A
      rbd: pass length, not op for osd completions · c47f9371
      Alex Elder 提交于
      The only thing type-specific osd completion functions do with their
      osd op parameter is (in some cases) extract the number of bytes
      transferred from it.  In the other cases, the xferred bytes field
      is not used, and total message data transfer byte count (which may
      well be zero) is used.
      
      Just set the object request transfer count in the main osd request
      callback function and provide that to the other routines.  There is
      then no longer any need to pass the op pointer to the type-specific
      completion routines, so drop those parameters.
      
      Stop doing anything with the total message data length.
      Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NSage Weil <sage@inktank.com>
      c47f9371
    • A
      rbd: move rbd_osd_trivial_callback() · 39bf2c5d
      Alex Elder 提交于
      This function is slightly out of place, probably the result
      of an errant automatic merge or something.
      Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NSage Weil <sage@inktank.com>
      39bf2c5d
  5. 26 2月, 2013 4 次提交
  6. 20 2月, 2013 5 次提交
  7. 19 2月, 2013 1 次提交
  8. 14 2月, 2013 7 次提交
    • A
      rbd: add barriers near done flag operations · 07741308
      Alex Elder 提交于
      Somehow, I missed this little item in Documentation/atomic_ops.txt:
          *** WARNING: atomic_read() and atomic_set() DO NOT IMPLY BARRIERS! ***
      
      Create and use some helper functions that include the proper memory
      barriers for manipulating the done field.
      Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      07741308
    • A
      rbd: turn off interrupts for open/remove locking · a14ea269
      Alex Elder 提交于
      This commit:
          bc7a62ee5 rbd: prevent open for image being removed
      added checking for removing rbd before allowing an open, and used
      the same request spinlock for protecting that and updating the open
      count as is used for the request queue.
      
      However it used the non-irq protected version of the spinlocks.
      Fix that.
      Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      a14ea269
    • A
      libceph: don't require r_num_pages for bio requests · 9cbb1d72
      Alex Elder 提交于
      There is a check in the completion path for osd requests that
      ensures the number of pages allocated is enough to hold the amount
      of incoming data expected.
      
      For bio requests coming from rbd the "number of pages" is not really
      meaningful (although total length would be).  So stop requiring that
      nr_pages be supplied for bio requests.  This is done by checking
      whether the pages pointer is null before checking the value of
      nr_pages.
      
      Note that this value is passed on to the messenger, but there it's
      only used for debugging--it's never used for validation.
      
      While here, change another spot that used r_pages in a debug message
      inappropriately, and also invalidate the r_con_filling_msg pointer
      after dropping a reference to it.
      
      This resolves:
          http://tracker.ceph.com/issues/3875Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      9cbb1d72
    • A
      rbd: don't take extra bio reference for osd client · 1e32d34c
      Alex Elder 提交于
      Currently, if the OSD client finds an osd request has had a bio list
      attached to it, it drops a reference to it (or rather, to the first
      entry on that list) when the request is released.
      
      The code that added that reference (i.e., the rbd client) is
      therefore required to take an extra reference to that first bio
      structure.
      
      The osd client doesn't really do anything with the bio pointer other
      than transfer it from the osd request structure to outgoing (for
      writes) and ingoing (for reads) messages.  So it really isn't the
      right place to be taking or dropping references.
      
      Furthermore, the rbd client already holds references to all bio
      structures it passes to the osd client, and holds them until the
      request is completed.  So there's no need for this extra reference
      whatsoever.
      
      So remove the bio_put() call in ceph_osdc_release_request(), as
      well as its matching bio_get() call in rbd_osd_req_create().
      
      This change could lead to a crash if old libceph.ko was used with
      new rbd.ko.  Add a compatibility check at rbd initialization time to
      avoid this possibilty.
      
      This resolves:
          http://tracker.ceph.com/issues/3798    and
          http://tracker.ceph.com/issues/3799Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      1e32d34c
    • A
      rbd: prevent open for image being removed · b82d167b
      Alex Elder 提交于
      An open request for a mapped rbd image can arrive while removal of
      that mapping is underway.  We need to prevent such an open request
      from succeeding.  (It appears that Maciej Galkiewicz ran into this
      problem.)
      
      Define and use a "removing" flag to indicate a mapping is getting
      removed.  Set it in the remove path after verifying nothing holds
      the device open.  And check it in the open path before allowing the
      open to proceed.  Acquire the rbd device's lock around each of these
      spots to avoid any races accessing the flags and open_count fields.
      
      This addresses:
          http://tracker.newdream.net/issues/3427Reported-by: NMaciej Galkiewicz <maciejgalkiewicz@ragnarson.com>
      Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      b82d167b
    • A
      rbd: define flags field, use it for exists flag · 6d292906
      Alex Elder 提交于
      Define a new rbd device flags field, manipulated using bit
      operations.  Replace the use of the current "exists" flag with a bit
      in this new "flags" field.  Add a little commentary about the
      "exists" flag, which does not need to be manipulated atomically.
      Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      6d292906
    • A
      rbd: don't drop watch requests on completion · 8eb87565
      Alex Elder 提交于
      When we register an osd request to linger, it means that request
      will stay around (under control of the osd client) until we've
      unregistered it.  We do that for an rbd image's header object, and
      we keep a pointer to the object request associated with it.
      
      Keep a reference to the watch object request for as long as it is
      registered to linger.  Drop it again after we've removed the linger
      registration.
      
      This resolves:
          http://tracker.ceph.com/issues/3937
      
      (Note: this originally came about because the osd client was
      issuing a callback more than once.  But that behavior will be
      changing soon, documented in tracker issue 3967.)
      Signed-off-by: NAlex Elder <elder@inktank.com>
      Reviewed-by: NJosh Durgin <josh.durgin@inktank.com>
      8eb87565