Пример #1
0
int
pycbc_tc_encode_key(pycbc_Bucket *conn,
                    PyObject **key,
                    void **buf,
                    size_t *nbuf)
{
    int rv;
    Py_ssize_t plen;

    PyObject *orig_key;
    PyObject *new_key = NULL;

    if (!conn->tc) {
        return encode_common(key, buf, nbuf, PYCBC_FMT_UTF8);
    }

    orig_key = *key;
    pycbc_assert(orig_key);

    rv = do_call_tc(conn, orig_key, NULL, &new_key, ENCODE_KEY);

    if (new_key == NULL || rv < 0) {
        return -1;
    }

    rv = PyBytes_AsStringAndSize(new_key, (char**)buf, &plen);

    if (rv == -1) {
        PYCBC_EXC_WRAP_KEY(PYCBC_EXC_ENCODING,
                           0,
                           "Couldn't convert encoded key to bytes. It is "
                           "possible that the Transcoder.encode_key method "
                           "returned an unexpected value",
                           new_key);

        Py_XDECREF(new_key);
        return -1;
    }

    if (plen == 0) {
        PYCBC_EXC_WRAP_KEY(PYCBC_EXC_ENCODING,
                           0,
                           "Transcoder.encode_key returned an empty string",
                           new_key);
        Py_XDECREF(new_key);
        return -1;
    }

    *nbuf = plen;
    *key = new_key;
    return 0;
}
Пример #2
0
int
pycbc_tc_decode_value(pycbc_Bucket *conn,
                       const void *value,
                       size_t nvalue,
                       lcb_uint32_t flags,
                       PyObject **pobj)
{
    PyObject *result = NULL;
    PyObject *pint = NULL;
    PyObject *pbuf = NULL;
    int rv;

    if (conn->data_passthrough == 0 && conn->tc == NULL) {
        return decode_common(pobj, value, nvalue, flags);
    }

    if (conn->data_passthrough) {
        *pobj = PyBytes_FromStringAndSize(value, nvalue);
        if (*pobj) {
            return 0;
        }
        return -1;
    }

    pbuf = PyBytes_FromStringAndSize(value, nvalue);
    if (!pbuf) {
        pbuf = PyBytes_FromString("");
    }

    pint = pycbc_IntFromUL(flags);
    if (!pint) {
        PYCBC_EXC_WRAP(PYCBC_EXC_INTERNAL, 0, "Couldn't create flags object");
        rv = -1;
        goto GT_DONE;
    }

    rv = do_call_tc(conn, pbuf, pint, &result, DECODE_VALUE);

    GT_DONE:
    Py_XDECREF(pint);
    Py_XDECREF(pbuf);

    if (rv < 0) {
        return -1;
    }

    *pobj = result;
    return 0;
}
Пример #3
0
int
pycbc_tc_encode_key(pycbc_Bucket *conn, PyObject *src, pycbc_pybuffer *dst)
{
    int rv;
    Py_ssize_t plen;

    if (!conn->tc) {
        rv = encode_common(src, dst, PYCBC_FMT_UTF8);
        if (rv == 0 && dst->length == 0) {
            PYCBC_EXCTHROW_EMPTYKEY();
            rv = -1;
        }
        return rv;
    }

    /* Swap out key and new key. Assign back later on */

    rv = do_call_tc(conn, src, NULL, &dst->pyobj, ENCODE_KEY);

    if (dst->pyobj == NULL || rv < 0) {
        dst->pyobj = NULL;
        return -1;
    }

    rv = PyBytes_AsStringAndSize(dst->pyobj, (char**)&dst->buffer, &plen);

    if (rv == -1) {
        PYCBC_EXC_WRAP_KEY(PYCBC_EXC_ENCODING,
                           0,
                           "Couldn't convert encoded key to bytes. It is "
                           "possible that the Transcoder.encode_key method "
                           "returned an unexpected value", dst->pyobj);

        PYCBC_PYBUF_RELEASE(dst);
        return -1;
    }

    if (plen == 0) {
        PYCBC_EXC_WRAP_KEY(PYCBC_EXC_ENCODING,
                           0,
                           "Transcoder.encode_key returned an empty string",
                           dst->pyobj);
        PYCBC_PYBUF_RELEASE(dst);
        return -1;
    }
    dst->length = plen;
    return 0;
}
Пример #4
0
int
pycbc_tc_decode_key(pycbc_Bucket *conn,
                     const void *key,
                     size_t nkey,
                     PyObject **pobj)
{
    PyObject *bobj;
    int rv = 0;
    if (conn->data_passthrough) {
        bobj = PyBytes_FromStringAndSize(key, nkey);
        *pobj = bobj;

    } else if (!conn->tc) {
        return decode_common(pobj, key, nkey, PYCBC_FMT_UTF8);

    } else {
        bobj = PyBytes_FromStringAndSize(key, nkey);
        if (bobj) {
            rv = do_call_tc(conn, bobj, NULL, pobj, DECODE_KEY);
            Py_XDECREF(bobj);

        } else {
            rv = -1;
        }

        if (rv < 0) {
            return -1;
        }
    }

    if (*pobj == NULL) {
        return -1;
    }

    if (PyObject_Hash(*pobj) == -1) {
        PYCBC_EXC_WRAP_KEY(PYCBC_EXC_ENCODING, 0,
                           "Transcoder.decode_key must return a hashable object",
                           *pobj);
        Py_XDECREF(*pobj);
        return -1;
    }

    return 0;
}
Пример #5
0
int
pycbc_tc_encode_value(pycbc_Bucket *conn,
                       PyObject **value,
                       PyObject *flag_v,
                       void **buf,
                       size_t *nbuf,
                       lcb_uint32_t *flags)
{
    PyObject *flags_obj;
    PyObject *orig_value;
    PyObject *new_value = NULL;
    PyObject *result_tuple = NULL;
    lcb_uint32_t flags_stackval;
    int rv;
    Py_ssize_t plen;

    orig_value = *value;

    if (!flag_v) {
        flag_v = conn->dfl_fmt;
    }

    if (!conn->tc) {

        if (flag_v == pycbc_helpers.fmt_auto) {
            flag_v = pycbc_tc_determine_format(*value);
        }

        rv = pycbc_get_u32(flag_v, &flags_stackval);
        if (rv < 0) {
            PYCBC_EXC_WRAP_OBJ(PYCBC_EXC_ARGUMENTS, 0,
                               "Bad value for flags",
                               flag_v);
            return -1;
        }

        *flags = flags_stackval;
        return encode_common(value, buf, nbuf, flags_stackval);
    }

    /**
     * Calling into Transcoder
     */

    rv = do_call_tc(conn, orig_value, flag_v, &result_tuple, ENCODE_VALUE);
    if (rv < 0) {
        return -1;
    }

    if (!PyTuple_Check(result_tuple) || PyTuple_GET_SIZE(result_tuple) != 2) {
        PYCBC_EXC_WRAP_EX(PYCBC_EXC_ENCODING, 0,
                          "Expected return of (bytes, flags)",
                          orig_value,
                          result_tuple);

        Py_XDECREF(result_tuple);
        return -1;

    }

    new_value = PyTuple_GET_ITEM(result_tuple, 0);
    flags_obj = PyTuple_GET_ITEM(result_tuple, 1);

    if (new_value == NULL || flags_obj == NULL) {
        PYCBC_EXC_WRAP_OBJ(PYCBC_EXC_INTERNAL, 0, "Tuple GET_ITEM had NULL",
                           result_tuple);

        Py_XDECREF(result_tuple);
        return -1;
    }

    rv = pycbc_get_u32(flags_obj, &flags_stackval);
    if (rv < 0) {
        Py_XDECREF(result_tuple);
        PYCBC_EXC_WRAP_VALUE(PYCBC_EXC_ENCODING, 0,
                             "Transcoder.encode_value() returned a bad "
                             "value for flags", orig_value);
        return -1;
    }

    *flags = flags_stackval;
    rv = PyBytes_AsStringAndSize(new_value, (char**)buf, &plen);
    if (rv == -1) {
        Py_XDECREF(result_tuple);

        PYCBC_EXC_WRAP_VALUE(PYCBC_EXC_ENCODING, 0,
                             "Value returned by Transcoder.encode_value() "
                             "could not be converted to bytes",
                orig_value);
        return -1;
    }

    *value = new_value;
    *nbuf = plen;

    Py_INCREF(new_value);
    Py_XDECREF(result_tuple);

    return 0;
}
Пример #6
0
int
pycbc_tc_encode_value(pycbc_Bucket *conn, PyObject *srcbuf, PyObject *srcflags,
                      pycbc_pybuffer *dstbuf, lcb_U32 *dstflags)
{
    PyObject *flags_obj;
    PyObject *new_value = NULL;
    PyObject *result_tuple = NULL;
    lcb_U32 flags_stackval;
    int rv;
    Py_ssize_t plen;

    if (!srcflags) {
        srcflags = conn->dfl_fmt;
    }

    if (!conn->tc) {
        if (srcflags == pycbc_helpers.fmt_auto) {
            srcflags = pycbc_tc_determine_format(srcbuf);
        }

        rv = pycbc_get_u32(srcflags, &flags_stackval);
        if (rv < 0) {
            PYCBC_EXC_WRAP_OBJ(PYCBC_EXC_ARGUMENTS, 0,
                               "Bad value for flags", srcflags);
            return -1;
        }

        *dstflags = flags_stackval;
        return encode_common(srcbuf, dstbuf, flags_stackval);
    }

    /**
     * Calling into Transcoder
     */
    rv = do_call_tc(conn, srcbuf, srcflags, &result_tuple, ENCODE_VALUE);
    if (rv < 0) {
        return -1;
    }

    if (!PyTuple_Check(result_tuple) || PyTuple_GET_SIZE(result_tuple) != 2) {
        PYCBC_EXC_WRAP_EX(PYCBC_EXC_ENCODING, 0,
                          "Expected return of (bytes, flags)",
                          srcbuf, result_tuple);

        Py_XDECREF(result_tuple);
        return -1;

    }

    new_value = PyTuple_GET_ITEM(result_tuple, 0);
    flags_obj = PyTuple_GET_ITEM(result_tuple, 1);

    if (new_value == NULL || flags_obj == NULL) {
        PYCBC_EXC_WRAP_OBJ(PYCBC_EXC_INTERNAL, 0, "Tuple GET_ITEM had NULL",
                           result_tuple);

        Py_XDECREF(result_tuple);
        return -1;
    }

    rv = pycbc_get_u32(flags_obj, &flags_stackval);
    if (rv < 0) {
        Py_XDECREF(result_tuple);
        PYCBC_EXC_WRAP_VALUE(PYCBC_EXC_ENCODING, 0,
                             "Transcoder.encode_value() returned a bad "
                             "value for flags", srcbuf);
        return -1;
    }

    *dstflags = flags_stackval;
    rv = PyBytes_AsStringAndSize(new_value, (char**)&dstbuf->buffer, &plen);
    if (rv == -1) {
        Py_XDECREF(result_tuple);
        PYCBC_EXC_WRAP_VALUE(PYCBC_EXC_ENCODING, 0,
                             "Value returned by Transcoder.encode_value() "
                             "could not be converted to bytes", srcbuf);
        return -1;
    }

    dstbuf->pyobj = new_value;
    dstbuf->length = plen;

    Py_INCREF(new_value);
    Py_XDECREF(result_tuple);

    return 0;
}