hgext/fsmonitor/pywatchman/bser.c
author Raphaël Gomès <rgomes@octobus.net>
Mon, 06 Dec 2021 11:10:59 +0100
branchstable
changeset 48411 5140461ee947
parent 43394 d359dfc15aca
permissions -rw-r--r--
fsmonitor: incorporate fixes for Python 3.10 (issue6612) Differential Revision: https://phab.mercurial-scm.org/D11862
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
     1
/*
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
     2
Copyright (c) 2013-2015, Facebook, Inc.
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
     3
All rights reserved.
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
     4
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
     5
Redistribution and use in source and binary forms, with or without
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
     6
modification, are permitted provided that the following conditions are met:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
     7
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
     8
 * Redistributions of source code must retain the above copyright notice,
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
     9
   this list of conditions and the following disclaimer.
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    10
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    11
 * Redistributions in binary form must reproduce the above copyright notice,
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    12
   this list of conditions and the following disclaimer in the documentation
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    13
   and/or other materials provided with the distribution.
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    14
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    15
 * Neither the name Facebook nor the names of its contributors may be used to
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    16
   endorse or promote products derived from this software without specific
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    17
   prior written permission.
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    18
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    19
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    20
AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    21
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    22
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    23
FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    24
DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    25
SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    26
CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    27
OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    28
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    29
*/
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    30
48411
5140461ee947 fsmonitor: incorporate fixes for Python 3.10 (issue6612)
Raphaël Gomès <rgomes@octobus.net>
parents: 43394
diff changeset
    31
#define PY_SSIZE_T_CLEAN
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    32
#include <Python.h>
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    33
#include <bytesobject.h>
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    34
#ifdef _MSC_VER
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    35
#define inline __inline
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    36
#if _MSC_VER >= 1800
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    37
#include <stdint.h>
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    38
#else
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    39
// The compiler associated with Python 2.7 on Windows doesn't ship
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    40
// with stdint.h, so define the small subset that we use here.
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    41
typedef __int8 int8_t;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    42
typedef __int16 int16_t;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    43
typedef __int32 int32_t;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    44
typedef __int64 int64_t;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    45
typedef unsigned __int8 uint8_t;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    46
typedef unsigned __int16 uint16_t;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    47
typedef unsigned __int32 uint32_t;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    48
typedef unsigned __int64 uint64_t;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    49
#define UINT32_MAX 4294967295U
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    50
#endif
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    51
#endif
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    52
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    53
// clang-format off
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    54
/* Return the smallest size int that can store the value */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    55
#define INT_SIZE(x) (((x) == ((int8_t)x))  ? 1 :    \
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    56
                     ((x) == ((int16_t)x)) ? 2 :    \
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    57
                     ((x) == ((int32_t)x)) ? 4 : 8)
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    58
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    59
#define BSER_ARRAY     0x00
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    60
#define BSER_OBJECT    0x01
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    61
#define BSER_BYTESTRING 0x02
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    62
#define BSER_INT8      0x03
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    63
#define BSER_INT16     0x04
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    64
#define BSER_INT32     0x05
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    65
#define BSER_INT64     0x06
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    66
#define BSER_REAL      0x07
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    67
#define BSER_TRUE      0x08
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    68
#define BSER_FALSE     0x09
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    69
#define BSER_NULL      0x0a
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    70
#define BSER_TEMPLATE  0x0b
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    71
#define BSER_SKIP      0x0c
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    72
#define BSER_UTF8STRING 0x0d
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    73
// clang-format on
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    74
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    75
// An immutable object representation of BSER_OBJECT.
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    76
// Rather than build a hash table, key -> value are obtained
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    77
// by walking the list of keys to determine the offset into
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    78
// the values array.  The assumption is that the number of
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    79
// array elements will be typically small (~6 for the top
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    80
// level query result and typically 3-5 for the file entries)
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    81
// so that the time overhead for this is small compared to
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    82
// using a proper hash table.  Even with this simplistic
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    83
// approach, this is still faster for the mercurial use case
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    84
// as it helps to eliminate creating N other objects to
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    85
// represent the stat information in the hgwatchman extension
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    86
// clang-format off
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    87
typedef struct {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    88
  PyObject_HEAD
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    89
  PyObject *keys;   // tuple of field names
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    90
  PyObject *values; // tuple of values
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    91
} bserObject;
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    92
// clang-format on
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    93
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    94
static Py_ssize_t bserobj_tuple_length(PyObject* o) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
    95
  bserObject* obj = (bserObject*)o;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    96
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    97
  return PySequence_Length(obj->keys);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    98
}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
    99
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   100
static PyObject* bserobj_tuple_item(PyObject* o, Py_ssize_t i) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   101
  bserObject* obj = (bserObject*)o;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   102
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   103
  return PySequence_GetItem(obj->values, i);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   104
}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   105
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   106
// clang-format off
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   107
static PySequenceMethods bserobj_sq = {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   108
  bserobj_tuple_length,      /* sq_length */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   109
  0,                         /* sq_concat */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   110
  0,                         /* sq_repeat */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   111
  bserobj_tuple_item,        /* sq_item */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   112
  0,                         /* sq_ass_item */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   113
  0,                         /* sq_contains */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   114
  0,                         /* sq_inplace_concat */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   115
  0                          /* sq_inplace_repeat */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   116
};
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   117
// clang-format on
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   118
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   119
static void bserobj_dealloc(PyObject* o) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   120
  bserObject* obj = (bserObject*)o;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   121
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   122
  Py_CLEAR(obj->keys);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   123
  Py_CLEAR(obj->values);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   124
  PyObject_Del(o);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   125
}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   126
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   127
static PyObject* bserobj_getattrro(PyObject* o, PyObject* name) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   128
  bserObject* obj = (bserObject*)o;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   129
  Py_ssize_t i, n;
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   130
  PyObject* name_bytes = NULL;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   131
  PyObject* ret = NULL;
43388
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   132
  const char* namestr = NULL;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   133
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   134
  if (PyIndex_Check(name)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   135
    i = PyNumber_AsSsize_t(name, PyExc_IndexError);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   136
    if (i == -1 && PyErr_Occurred()) {
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   137
      goto bail;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   138
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   139
43388
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   140
    if (i == 8 && PySequence_Size(obj->values) < 9) {
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   141
      // Hack alert: Python 3 removed support for os.stat().st_mtime
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   142
      // being an integer.Instead, if you need an integer, you have to
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   143
      // use os.stat()[stat.ST_MTIME] instead. stat.ST_MTIME is 8, and
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   144
      // our stat tuples are shorter than that, so we can detect
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   145
      // requests for index 8 on tuples shorter than that and return
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   146
      // st_mtime instead.
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   147
      namestr = "st_mtime";
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   148
    } else {
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   149
      ret = PySequence_GetItem(obj->values, i);
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   150
      goto bail;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   151
    }
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   152
  } else {
43388
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   153
    // We can be passed in Unicode objects here -- we don't support anything other
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   154
    // than UTF-8 for keys.
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   155
    if (PyUnicode_Check(name)) {
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   156
      name_bytes = PyUnicode_AsUTF8String(name);
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   157
      if (name_bytes == NULL) {
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   158
        goto bail;
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   159
      }
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   160
      namestr = PyBytes_AsString(name_bytes);
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   161
    } else {
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   162
      namestr = PyBytes_AsString(name);
51316de92ad0 fsmonitor: reapply b1f62cd39b5c
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43385
diff changeset
   163
    }
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   164
  }
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   165
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   166
  if (namestr == NULL) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   167
    goto bail;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   168
  }
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   169
  // hack^Wfeature to allow mercurial to use "st_size" to reference "size"
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   170
  if (!strncmp(namestr, "st_", 3)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   171
    namestr += 3;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   172
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   173
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   174
  n = PyTuple_GET_SIZE(obj->keys);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   175
  for (i = 0; i < n; i++) {
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   176
    const char* item_name = NULL;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   177
    PyObject* key = PyTuple_GET_ITEM(obj->keys, i);
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   178
43394
d359dfc15aca fsmonitor: handle unicode keys in tuples
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43388
diff changeset
   179
    if (PyUnicode_Check(key)) {
d359dfc15aca fsmonitor: handle unicode keys in tuples
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43388
diff changeset
   180
#if PY_MAJOR_VERSION >= 3
d359dfc15aca fsmonitor: handle unicode keys in tuples
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43388
diff changeset
   181
      item_name = PyUnicode_AsUTF8(key);
d359dfc15aca fsmonitor: handle unicode keys in tuples
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43388
diff changeset
   182
#else
d359dfc15aca fsmonitor: handle unicode keys in tuples
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43388
diff changeset
   183
      PyObject* utf = PyUnicode_AsEncodedString(key, "utf-8", "ignore");
d359dfc15aca fsmonitor: handle unicode keys in tuples
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43388
diff changeset
   184
      if (utf == NULL) {
d359dfc15aca fsmonitor: handle unicode keys in tuples
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43388
diff changeset
   185
        goto bail;
d359dfc15aca fsmonitor: handle unicode keys in tuples
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43388
diff changeset
   186
      }
d359dfc15aca fsmonitor: handle unicode keys in tuples
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43388
diff changeset
   187
      item_name = PyBytes_AsString(utf);
d359dfc15aca fsmonitor: handle unicode keys in tuples
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43388
diff changeset
   188
#endif
d359dfc15aca fsmonitor: handle unicode keys in tuples
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43388
diff changeset
   189
    } else {
d359dfc15aca fsmonitor: handle unicode keys in tuples
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43388
diff changeset
   190
      item_name = PyBytes_AsString(key);
d359dfc15aca fsmonitor: handle unicode keys in tuples
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43388
diff changeset
   191
    }
d359dfc15aca fsmonitor: handle unicode keys in tuples
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43388
diff changeset
   192
    if (item_name == NULL) {
d359dfc15aca fsmonitor: handle unicode keys in tuples
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43388
diff changeset
   193
      goto bail;
d359dfc15aca fsmonitor: handle unicode keys in tuples
Gregory Szorc <gregory.szorc@gmail.com>
parents: 43388
diff changeset
   194
    }
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   195
    if (!strcmp(item_name, namestr)) {
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   196
      ret = PySequence_GetItem(obj->values, i);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   197
      goto bail;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   198
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   199
  }
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   200
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   201
  PyErr_Format(
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   202
      PyExc_AttributeError, "bserobject has no attribute '%.400s'", namestr);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   203
bail:
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   204
  Py_XDECREF(name_bytes);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   205
  return ret;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   206
}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   207
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   208
// clang-format off
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   209
static PyMappingMethods bserobj_map = {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   210
  bserobj_tuple_length,     /* mp_length */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   211
  bserobj_getattrro,        /* mp_subscript */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   212
  0                         /* mp_ass_subscript */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   213
};
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   214
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   215
PyTypeObject bserObjectType = {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   216
  PyVarObject_HEAD_INIT(NULL, 0)
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   217
  "bserobj_tuple",           /* tp_name */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   218
  sizeof(bserObject),        /* tp_basicsize */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   219
  0,                         /* tp_itemsize */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   220
  bserobj_dealloc,           /* tp_dealloc */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   221
  0,                         /* tp_print */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   222
  0,                         /* tp_getattr */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   223
  0,                         /* tp_setattr */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   224
  0,                         /* tp_compare */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   225
  0,                         /* tp_repr */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   226
  0,                         /* tp_as_number */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   227
  &bserobj_sq,               /* tp_as_sequence */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   228
  &bserobj_map,              /* tp_as_mapping */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   229
  0,                         /* tp_hash  */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   230
  0,                         /* tp_call */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   231
  0,                         /* tp_str */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   232
  bserobj_getattrro,         /* tp_getattro */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   233
  0,                         /* tp_setattro */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   234
  0,                         /* tp_as_buffer */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   235
  Py_TPFLAGS_DEFAULT,        /* tp_flags */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   236
  "bserobj tuple",           /* tp_doc */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   237
  0,                         /* tp_traverse */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   238
  0,                         /* tp_clear */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   239
  0,                         /* tp_richcompare */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   240
  0,                         /* tp_weaklistoffset */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   241
  0,                         /* tp_iter */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   242
  0,                         /* tp_iternext */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   243
  0,                         /* tp_methods */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   244
  0,                         /* tp_members */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   245
  0,                         /* tp_getset */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   246
  0,                         /* tp_base */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   247
  0,                         /* tp_dict */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   248
  0,                         /* tp_descr_get */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   249
  0,                         /* tp_descr_set */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   250
  0,                         /* tp_dictoffset */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   251
  0,                         /* tp_init */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   252
  0,                         /* tp_alloc */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   253
  0,                         /* tp_new */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   254
};
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   255
// clang-format on
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   256
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   257
typedef struct loads_ctx {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   258
  int mutable;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   259
  const char* value_encoding;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   260
  const char* value_errors;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   261
  uint32_t bser_version;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   262
  uint32_t bser_capabilities;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   263
} unser_ctx_t;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   264
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   265
static PyObject*
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   266
bser_loads_recursive(const char** ptr, const char* end, const unser_ctx_t* ctx);
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   267
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   268
static const char bser_true = BSER_TRUE;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   269
static const char bser_false = BSER_FALSE;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   270
static const char bser_null = BSER_NULL;
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   271
static const char bser_bytestring_hdr = BSER_BYTESTRING;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   272
static const char bser_array_hdr = BSER_ARRAY;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   273
static const char bser_object_hdr = BSER_OBJECT;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   274
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   275
static inline uint32_t next_power_2(uint32_t n) {
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   276
  n |= (n >> 16);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   277
  n |= (n >> 8);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   278
  n |= (n >> 4);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   279
  n |= (n >> 2);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   280
  n |= (n >> 1);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   281
  return n + 1;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   282
}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   283
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   284
// A buffer we use for building up the serialized result
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   285
struct bser_buffer {
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   286
  char* buf;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   287
  int wpos, allocd;
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   288
  uint32_t bser_version;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   289
  uint32_t capabilities;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   290
};
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   291
typedef struct bser_buffer bser_t;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   292
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   293
static int bser_append(bser_t* bser, const char* data, uint32_t len) {
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   294
  int newlen = next_power_2(bser->wpos + len);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   295
  if (newlen > bser->allocd) {
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   296
    char* nbuf = realloc(bser->buf, newlen);
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   297
    if (!nbuf) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   298
      return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   299
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   300
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   301
    bser->buf = nbuf;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   302
    bser->allocd = newlen;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   303
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   304
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   305
  memcpy(bser->buf + bser->wpos, data, len);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   306
  bser->wpos += len;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   307
  return 1;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   308
}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   309
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   310
static int bser_init(bser_t* bser, uint32_t version, uint32_t capabilities) {
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   311
  bser->allocd = 8192;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   312
  bser->wpos = 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   313
  bser->buf = malloc(bser->allocd);
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   314
  bser->bser_version = version;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   315
  bser->capabilities = capabilities;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   316
  if (!bser->buf) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   317
    return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   318
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   319
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   320
// Leave room for the serialization header, which includes
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   321
// our overall length.  To make things simpler, we'll use an
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   322
// int32 for the header
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   323
#define EMPTY_HEADER "\x00\x01\x05\x00\x00\x00\x00"
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   324
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   325
// Version 2 also carries an integer indicating the capabilities. The
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   326
// capabilities integer comes before the PDU size.
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   327
#define EMPTY_HEADER_V2 "\x00\x02\x00\x00\x00\x00\x05\x00\x00\x00\x00"
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   328
  if (version == 2) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   329
    bser_append(bser, EMPTY_HEADER_V2, sizeof(EMPTY_HEADER_V2) - 1);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   330
  } else {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   331
    bser_append(bser, EMPTY_HEADER, sizeof(EMPTY_HEADER) - 1);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   332
  }
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   333
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   334
  return 1;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   335
}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   336
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   337
static void bser_dtor(bser_t* bser) {
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   338
  free(bser->buf);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   339
  bser->buf = NULL;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   340
}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   341
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   342
static int bser_long(bser_t* bser, int64_t val) {
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   343
  int8_t i8;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   344
  int16_t i16;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   345
  int32_t i32;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   346
  int64_t i64;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   347
  char sz;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   348
  int size = INT_SIZE(val);
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   349
  char* iptr;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   350
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   351
  switch (size) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   352
    case 1:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   353
      sz = BSER_INT8;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   354
      i8 = (int8_t)val;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   355
      iptr = (char*)&i8;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   356
      break;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   357
    case 2:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   358
      sz = BSER_INT16;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   359
      i16 = (int16_t)val;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   360
      iptr = (char*)&i16;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   361
      break;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   362
    case 4:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   363
      sz = BSER_INT32;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   364
      i32 = (int32_t)val;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   365
      iptr = (char*)&i32;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   366
      break;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   367
    case 8:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   368
      sz = BSER_INT64;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   369
      i64 = (int64_t)val;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   370
      iptr = (char*)&i64;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   371
      break;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   372
    default:
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   373
      PyErr_SetString(PyExc_RuntimeError, "Cannot represent this long value!?");
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   374
      return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   375
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   376
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   377
  if (!bser_append(bser, &sz, sizeof(sz))) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   378
    return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   379
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   380
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   381
  return bser_append(bser, iptr, size);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   382
}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   383
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   384
static int bser_bytestring(bser_t* bser, PyObject* sval) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   385
  char* buf = NULL;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   386
  Py_ssize_t len;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   387
  int res;
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   388
  PyObject* utf = NULL;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   389
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   390
  if (PyUnicode_Check(sval)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   391
    utf = PyUnicode_AsEncodedString(sval, "utf-8", "ignore");
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   392
    sval = utf;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   393
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   394
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   395
  res = PyBytes_AsStringAndSize(sval, &buf, &len);
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   396
  if (res == -1) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   397
    res = 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   398
    goto out;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   399
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   400
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   401
  if (!bser_append(bser, &bser_bytestring_hdr, sizeof(bser_bytestring_hdr))) {
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   402
    res = 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   403
    goto out;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   404
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   405
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   406
  if (!bser_long(bser, len)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   407
    res = 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   408
    goto out;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   409
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   410
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   411
  if (len > UINT32_MAX) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   412
    PyErr_Format(PyExc_ValueError, "string too big");
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   413
    res = 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   414
    goto out;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   415
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   416
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   417
  res = bser_append(bser, buf, (uint32_t)len);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   418
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   419
out:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   420
  if (utf) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   421
    Py_DECREF(utf);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   422
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   423
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   424
  return res;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   425
}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   426
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   427
static int bser_recursive(bser_t* bser, PyObject* val) {
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   428
  if (PyBool_Check(val)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   429
    if (val == Py_True) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   430
      return bser_append(bser, &bser_true, sizeof(bser_true));
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   431
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   432
    return bser_append(bser, &bser_false, sizeof(bser_false));
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   433
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   434
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   435
  if (val == Py_None) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   436
    return bser_append(bser, &bser_null, sizeof(bser_null));
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   437
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   438
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   439
// Python 3 has one integer type.
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   440
#if PY_MAJOR_VERSION < 3
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   441
  if (PyInt_Check(val)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   442
    return bser_long(bser, PyInt_AS_LONG(val));
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   443
  }
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   444
#endif // PY_MAJOR_VERSION < 3
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   445
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   446
  if (PyLong_Check(val)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   447
    return bser_long(bser, PyLong_AsLongLong(val));
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   448
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   449
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   450
  if (PyBytes_Check(val) || PyUnicode_Check(val)) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   451
    return bser_bytestring(bser, val);
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   452
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   453
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   454
  if (PyFloat_Check(val)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   455
    double dval = PyFloat_AS_DOUBLE(val);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   456
    char sz = BSER_REAL;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   457
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   458
    if (!bser_append(bser, &sz, sizeof(sz))) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   459
      return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   460
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   461
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   462
    return bser_append(bser, (char*)&dval, sizeof(dval));
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   463
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   464
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   465
  if (PyList_Check(val)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   466
    Py_ssize_t i, len = PyList_GET_SIZE(val);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   467
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   468
    if (!bser_append(bser, &bser_array_hdr, sizeof(bser_array_hdr))) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   469
      return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   470
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   471
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   472
    if (!bser_long(bser, len)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   473
      return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   474
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   475
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   476
    for (i = 0; i < len; i++) {
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   477
      PyObject* ele = PyList_GET_ITEM(val, i);
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   478
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   479
      if (!bser_recursive(bser, ele)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   480
        return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   481
      }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   482
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   483
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   484
    return 1;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   485
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   486
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   487
  if (PyTuple_Check(val)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   488
    Py_ssize_t i, len = PyTuple_GET_SIZE(val);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   489
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   490
    if (!bser_append(bser, &bser_array_hdr, sizeof(bser_array_hdr))) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   491
      return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   492
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   493
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   494
    if (!bser_long(bser, len)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   495
      return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   496
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   497
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   498
    for (i = 0; i < len; i++) {
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   499
      PyObject* ele = PyTuple_GET_ITEM(val, i);
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   500
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   501
      if (!bser_recursive(bser, ele)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   502
        return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   503
      }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   504
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   505
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   506
    return 1;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   507
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   508
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   509
  if (PyMapping_Check(val)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   510
    Py_ssize_t len = PyMapping_Length(val);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   511
    Py_ssize_t pos = 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   512
    PyObject *key, *ele;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   513
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   514
    if (!bser_append(bser, &bser_object_hdr, sizeof(bser_object_hdr))) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   515
      return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   516
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   517
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   518
    if (!bser_long(bser, len)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   519
      return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   520
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   521
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   522
    while (PyDict_Next(val, &pos, &key, &ele)) {
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   523
      if (!bser_bytestring(bser, key)) {
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   524
        return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   525
      }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   526
      if (!bser_recursive(bser, ele)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   527
        return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   528
      }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   529
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   530
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   531
    return 1;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   532
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   533
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   534
  PyErr_SetString(PyExc_ValueError, "Unsupported value type");
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   535
  return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   536
}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   537
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   538
static PyObject* bser_dumps(PyObject* self, PyObject* args, PyObject* kw) {
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   539
  PyObject *val = NULL, *res;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   540
  bser_t bser;
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   541
  uint32_t len, bser_version = 1, bser_capabilities = 0;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   542
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   543
  static char* kw_list[] = {"val", "version", "capabilities", NULL};
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   544
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   545
  if (!PyArg_ParseTupleAndKeywords(
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   546
          args,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   547
          kw,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   548
          "O|ii:dumps",
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   549
          kw_list,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   550
          &val,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   551
          &bser_version,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   552
          &bser_capabilities)) {
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   553
    return NULL;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   554
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   555
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   556
  if (!bser_init(&bser, bser_version, bser_capabilities)) {
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   557
    return PyErr_NoMemory();
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   558
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   559
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   560
  if (!bser_recursive(&bser, val)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   561
    bser_dtor(&bser);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   562
    if (errno == ENOMEM) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   563
      return PyErr_NoMemory();
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   564
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   565
    // otherwise, we've already set the error to something reasonable
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   566
    return NULL;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   567
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   568
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   569
  // Now fill in the overall length
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   570
  if (bser_version == 1) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   571
    len = bser.wpos - (sizeof(EMPTY_HEADER) - 1);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   572
    memcpy(bser.buf + 3, &len, sizeof(len));
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   573
  } else {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   574
    len = bser.wpos - (sizeof(EMPTY_HEADER_V2) - 1);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   575
    // The BSER capabilities block comes before the PDU length
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   576
    memcpy(bser.buf + 2, &bser_capabilities, sizeof(bser_capabilities));
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   577
    memcpy(bser.buf + 7, &len, sizeof(len));
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   578
  }
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   579
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   580
  res = PyBytes_FromStringAndSize(bser.buf, bser.wpos);
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   581
  bser_dtor(&bser);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   582
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   583
  return res;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   584
}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   585
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   586
int bunser_int(const char** ptr, const char* end, int64_t* val) {
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   587
  int needed;
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   588
  const char* buf = *ptr;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   589
  int8_t i8;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   590
  int16_t i16;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   591
  int32_t i32;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   592
  int64_t i64;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   593
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   594
  switch (buf[0]) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   595
    case BSER_INT8:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   596
      needed = 2;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   597
      break;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   598
    case BSER_INT16:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   599
      needed = 3;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   600
      break;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   601
    case BSER_INT32:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   602
      needed = 5;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   603
      break;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   604
    case BSER_INT64:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   605
      needed = 9;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   606
      break;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   607
    default:
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   608
      PyErr_Format(
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   609
          PyExc_ValueError, "invalid bser int encoding 0x%02x", buf[0]);
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   610
      return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   611
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   612
  if (end - buf < needed) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   613
    PyErr_SetString(PyExc_ValueError, "input buffer to small for int encoding");
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   614
    return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   615
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   616
  *ptr = buf + needed;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   617
  switch (buf[0]) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   618
    case BSER_INT8:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   619
      memcpy(&i8, buf + 1, sizeof(i8));
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   620
      *val = i8;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   621
      return 1;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   622
    case BSER_INT16:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   623
      memcpy(&i16, buf + 1, sizeof(i16));
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   624
      *val = i16;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   625
      return 1;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   626
    case BSER_INT32:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   627
      memcpy(&i32, buf + 1, sizeof(i32));
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   628
      *val = i32;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   629
      return 1;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   630
    case BSER_INT64:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   631
      memcpy(&i64, buf + 1, sizeof(i64));
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   632
      *val = i64;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   633
      return 1;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   634
    default:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   635
      return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   636
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   637
}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   638
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   639
static int bunser_bytestring(
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   640
    const char** ptr,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   641
    const char* end,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   642
    const char** start,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   643
    int64_t* len) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   644
  const char* buf = *ptr;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   645
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   646
  // skip string marker
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   647
  buf++;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   648
  if (!bunser_int(&buf, end, len)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   649
    return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   650
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   651
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   652
  if (buf + *len > end) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   653
    PyErr_Format(PyExc_ValueError, "invalid string length in bser data");
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   654
    return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   655
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   656
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   657
  *ptr = buf + *len;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   658
  *start = buf;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   659
  return 1;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   660
}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   661
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   662
static PyObject*
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   663
bunser_array(const char** ptr, const char* end, const unser_ctx_t* ctx) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   664
  const char* buf = *ptr;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   665
  int64_t nitems, i;
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   666
  int mutable = ctx->mutable;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   667
  PyObject* res;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   668
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   669
  // skip array header
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   670
  buf++;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   671
  if (!bunser_int(&buf, end, &nitems)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   672
    return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   673
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   674
  *ptr = buf;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   675
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   676
  if (nitems > LONG_MAX) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   677
    PyErr_Format(PyExc_ValueError, "too many items for python array");
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   678
    return NULL;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   679
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   680
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   681
  if (mutable) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   682
    res = PyList_New((Py_ssize_t)nitems);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   683
  } else {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   684
    res = PyTuple_New((Py_ssize_t)nitems);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   685
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   686
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   687
  for (i = 0; i < nitems; i++) {
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   688
    PyObject* ele = bser_loads_recursive(ptr, end, ctx);
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   689
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   690
    if (!ele) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   691
      Py_DECREF(res);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   692
      return NULL;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   693
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   694
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   695
    if (mutable) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   696
      PyList_SET_ITEM(res, i, ele);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   697
    } else {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   698
      PyTuple_SET_ITEM(res, i, ele);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   699
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   700
    // DECREF(ele) not required as SET_ITEM steals the ref
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   701
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   702
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   703
  return res;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   704
}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   705
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   706
static PyObject*
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   707
bunser_object(const char** ptr, const char* end, const unser_ctx_t* ctx) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   708
  const char* buf = *ptr;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   709
  int64_t nitems, i;
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   710
  int mutable = ctx->mutable;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   711
  PyObject* res;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   712
  bserObject* obj;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   713
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   714
  // skip array header
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   715
  buf++;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   716
  if (!bunser_int(&buf, end, &nitems)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   717
    return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   718
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   719
  *ptr = buf;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   720
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   721
  if (mutable) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   722
    res = PyDict_New();
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   723
  } else {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   724
    obj = PyObject_New(bserObject, &bserObjectType);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   725
    obj->keys = PyTuple_New((Py_ssize_t)nitems);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   726
    obj->values = PyTuple_New((Py_ssize_t)nitems);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   727
    res = (PyObject*)obj;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   728
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   729
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   730
  for (i = 0; i < nitems; i++) {
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   731
    const char* keystr;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   732
    int64_t keylen;
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   733
    PyObject* key;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   734
    PyObject* ele;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   735
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   736
    if (!bunser_bytestring(ptr, end, &keystr, &keylen)) {
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   737
      Py_DECREF(res);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   738
      return NULL;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   739
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   740
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   741
    if (keylen > LONG_MAX) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   742
      PyErr_Format(PyExc_ValueError, "string too big for python");
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   743
      Py_DECREF(res);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   744
      return NULL;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   745
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   746
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   747
    if (mutable) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   748
      // This will interpret the key as UTF-8.
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   749
      key = PyUnicode_FromStringAndSize(keystr, (Py_ssize_t)keylen);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   750
    } else {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   751
      // For immutable objects we'll manage key lookups, so we can avoid going
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   752
      // through the Unicode APIs. This avoids a potentially expensive and
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   753
      // definitely unnecessary conversion to UTF-16 and back for Python 2.
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   754
      // TODO: On Python 3 the Unicode APIs are smarter: we might be able to use
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   755
      // Unicode keys there without an appreciable performance loss.
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   756
      key = PyBytes_FromStringAndSize(keystr, (Py_ssize_t)keylen);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   757
    }
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   758
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   759
    if (!key) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   760
      Py_DECREF(res);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   761
      return NULL;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   762
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   763
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   764
    ele = bser_loads_recursive(ptr, end, ctx);
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   765
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   766
    if (!ele) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   767
      Py_DECREF(key);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   768
      Py_DECREF(res);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   769
      return NULL;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   770
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   771
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   772
    if (mutable) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   773
      PyDict_SetItem(res, key, ele);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   774
      Py_DECREF(key);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   775
      Py_DECREF(ele);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   776
    } else {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   777
      /* PyTuple_SET_ITEM steals ele, key */
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   778
      PyTuple_SET_ITEM(obj->values, i, ele);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   779
      PyTuple_SET_ITEM(obj->keys, i, key);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   780
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   781
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   782
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   783
  return res;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   784
}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   785
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   786
static PyObject*
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   787
bunser_template(const char** ptr, const char* end, const unser_ctx_t* ctx) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   788
  const char* buf = *ptr;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   789
  int64_t nitems, i;
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   790
  int mutable = ctx->mutable;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   791
  PyObject* arrval;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   792
  PyObject* keys;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   793
  Py_ssize_t numkeys, keyidx;
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   794
  unser_ctx_t keys_ctx = {0};
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   795
  if (mutable) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   796
    keys_ctx.mutable = 1;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   797
    // Decode keys as UTF-8 in this case.
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   798
    keys_ctx.value_encoding = "utf-8";
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   799
    keys_ctx.value_errors = "strict";
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   800
  } else {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   801
    // Treat keys as bytestrings in this case -- we'll do Unicode conversions at
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   802
    // lookup time.
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   803
  }
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   804
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   805
  if (buf[1] != BSER_ARRAY) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   806
    PyErr_Format(PyExc_ValueError, "Expect ARRAY to follow TEMPLATE");
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   807
    return NULL;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   808
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   809
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   810
  // skip header
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   811
  buf++;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   812
  *ptr = buf;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   813
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   814
  // Load template keys.
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   815
  // For keys we don't want to do any decoding right now.
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   816
  keys = bunser_array(ptr, end, &keys_ctx);
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   817
  if (!keys) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   818
    return NULL;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   819
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   820
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   821
  numkeys = PySequence_Length(keys);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   822
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   823
  // Load number of array elements
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   824
  if (!bunser_int(ptr, end, &nitems)) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   825
    Py_DECREF(keys);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   826
    return 0;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   827
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   828
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   829
  if (nitems > LONG_MAX) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   830
    PyErr_Format(PyExc_ValueError, "Too many items for python");
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   831
    Py_DECREF(keys);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   832
    return NULL;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   833
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   834
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   835
  arrval = PyList_New((Py_ssize_t)nitems);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   836
  if (!arrval) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   837
    Py_DECREF(keys);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   838
    return NULL;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   839
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   840
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   841
  for (i = 0; i < nitems; i++) {
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   842
    PyObject* dict = NULL;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   843
    bserObject* obj = NULL;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   844
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   845
    if (mutable) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   846
      dict = PyDict_New();
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   847
    } else {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   848
      obj = PyObject_New(bserObject, &bserObjectType);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   849
      if (obj) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   850
        obj->keys = keys;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   851
        Py_INCREF(obj->keys);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   852
        obj->values = PyTuple_New(numkeys);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   853
      }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   854
      dict = (PyObject*)obj;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   855
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   856
    if (!dict) {
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   857
    fail:
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   858
      Py_DECREF(keys);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   859
      Py_DECREF(arrval);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   860
      return NULL;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   861
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   862
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   863
    for (keyidx = 0; keyidx < numkeys; keyidx++) {
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   864
      PyObject* key;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   865
      PyObject* ele;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   866
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   867
      if (**ptr == BSER_SKIP) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   868
        *ptr = *ptr + 1;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   869
        ele = Py_None;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   870
        Py_INCREF(ele);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   871
      } else {
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   872
        ele = bser_loads_recursive(ptr, end, ctx);
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   873
      }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   874
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   875
      if (!ele) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   876
        goto fail;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   877
      }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   878
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   879
      if (mutable) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   880
        key = PyList_GET_ITEM(keys, keyidx);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   881
        PyDict_SetItem(dict, key, ele);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   882
        Py_DECREF(ele);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   883
      } else {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   884
        PyTuple_SET_ITEM(obj->values, keyidx, ele);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   885
        // DECREF(ele) not required as SET_ITEM steals the ref
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   886
      }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   887
    }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   888
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   889
    PyList_SET_ITEM(arrval, i, dict);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   890
    // DECREF(obj) not required as SET_ITEM steals the ref
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   891
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   892
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   893
  Py_DECREF(keys);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   894
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   895
  return arrval;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   896
}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   897
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   898
static PyObject* bser_loads_recursive(
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   899
    const char** ptr,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   900
    const char* end,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   901
    const unser_ctx_t* ctx) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   902
  const char* buf = *ptr;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   903
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   904
  switch (buf[0]) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   905
    case BSER_INT8:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   906
    case BSER_INT16:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   907
    case BSER_INT32:
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   908
    case BSER_INT64: {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   909
      int64_t ival;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   910
      if (!bunser_int(ptr, end, &ival)) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   911
        return NULL;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   912
      }
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   913
// Python 3 has one integer type.
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   914
#if PY_MAJOR_VERSION >= 3
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   915
      return PyLong_FromLongLong(ival);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   916
#else
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   917
      if (ival < LONG_MIN || ival > LONG_MAX) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   918
        return PyLong_FromLongLong(ival);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   919
      }
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   920
      return PyInt_FromSsize_t(Py_SAFE_DOWNCAST(ival, int64_t, Py_ssize_t));
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   921
#endif // PY_MAJOR_VERSION >= 3
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   922
    }
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   923
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   924
    case BSER_REAL: {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   925
      double dval;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   926
      memcpy(&dval, buf + 1, sizeof(dval));
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   927
      *ptr = buf + 1 + sizeof(double);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   928
      return PyFloat_FromDouble(dval);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   929
    }
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   930
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   931
    case BSER_TRUE:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   932
      *ptr = buf + 1;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   933
      Py_INCREF(Py_True);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   934
      return Py_True;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   935
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   936
    case BSER_FALSE:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   937
      *ptr = buf + 1;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   938
      Py_INCREF(Py_False);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   939
      return Py_False;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   940
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   941
    case BSER_NULL:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   942
      *ptr = buf + 1;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   943
      Py_INCREF(Py_None);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   944
      return Py_None;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   945
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   946
    case BSER_BYTESTRING: {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   947
      const char* start;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   948
      int64_t len;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   949
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   950
      if (!bunser_bytestring(ptr, end, &start, &len)) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   951
        return NULL;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   952
      }
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   953
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   954
      if (len > LONG_MAX) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   955
        PyErr_Format(PyExc_ValueError, "string too long for python");
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   956
        return NULL;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   957
      }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   958
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   959
      if (ctx->value_encoding != NULL) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   960
        return PyUnicode_Decode(
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   961
            start, (long)len, ctx->value_encoding, ctx->value_errors);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   962
      } else {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   963
        return PyBytes_FromStringAndSize(start, (long)len);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   964
      }
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   965
    }
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   966
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   967
    case BSER_UTF8STRING: {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   968
      const char* start;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   969
      int64_t len;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   970
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   971
      if (!bunser_bytestring(ptr, end, &start, &len)) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   972
        return NULL;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   973
      }
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   974
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   975
      if (len > LONG_MAX) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   976
        PyErr_Format(PyExc_ValueError, "string too long for python");
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   977
        return NULL;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   978
      }
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   979
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   980
      return PyUnicode_Decode(start, (long)len, "utf-8", "strict");
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   981
    }
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   982
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   983
    case BSER_ARRAY:
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   984
      return bunser_array(ptr, end, ctx);
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   985
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   986
    case BSER_OBJECT:
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   987
      return bunser_object(ptr, end, ctx);
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   988
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   989
    case BSER_TEMPLATE:
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   990
      return bunser_template(ptr, end, ctx);
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   991
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   992
    default:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   993
      PyErr_Format(PyExc_ValueError, "unhandled bser opcode 0x%02x", buf[0]);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   994
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   995
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   996
  return NULL;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   997
}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
   998
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
   999
static int _pdu_info_helper(
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1000
    const char* data,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1001
    const char* end,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1002
    uint32_t* bser_version_out,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1003
    uint32_t* bser_capabilities_out,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1004
    int64_t* expected_len_out,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1005
    off_t* position_out) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1006
  uint32_t bser_version;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1007
  uint32_t bser_capabilities = 0;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1008
  int64_t expected_len;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1009
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1010
  const char* start;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1011
  start = data;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1012
  // Validate the header and length
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1013
  if (memcmp(data, EMPTY_HEADER, 2) == 0) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1014
    bser_version = 1;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1015
  } else if (memcmp(data, EMPTY_HEADER_V2, 2) == 0) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1016
    bser_version = 2;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1017
  } else {
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1018
    PyErr_SetString(PyExc_ValueError, "invalid bser header");
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1019
    return 0;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1020
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1021
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1022
  data += 2;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1023
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1024
  if (bser_version == 2) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1025
    // Expect an integer telling us what capabilities are supported by the
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1026
    // remote server (currently unused).
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1027
    if (!memcpy(&bser_capabilities, &data, sizeof(bser_capabilities))) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1028
      return 0;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1029
    }
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1030
    data += sizeof(bser_capabilities);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1031
  }
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1032
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1033
  // Expect an integer telling us how big the rest of the data
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1034
  // should be
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1035
  if (!bunser_int(&data, end, &expected_len)) {
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1036
    return 0;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1037
  }
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1038
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1039
  *bser_version_out = bser_version;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1040
  *bser_capabilities_out = (uint32_t)bser_capabilities;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1041
  *expected_len_out = expected_len;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1042
  *position_out = (off_t)(data - start);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1043
  return 1;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1044
}
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1045
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1046
// This function parses the PDU header and provides info about the packet
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1047
// Returns false if unsuccessful
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1048
static int pdu_info_helper(
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1049
    PyObject* self,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1050
    PyObject* args,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1051
    uint32_t* bser_version_out,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1052
    uint32_t* bser_capabilities_out,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1053
    int64_t* total_len_out) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1054
  const char* start = NULL;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1055
  const char* data = NULL;
48411
5140461ee947 fsmonitor: incorporate fixes for Python 3.10 (issue6612)
Raphaël Gomès <rgomes@octobus.net>
parents: 43394
diff changeset
  1056
  Py_ssize_t datalen = 0;
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1057
  const char* end;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1058
  int64_t expected_len;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1059
  off_t position;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1060
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1061
  if (!PyArg_ParseTuple(args, "s#", &start, &datalen)) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1062
    return 0;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1063
  }
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1064
  data = start;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1065
  end = data + datalen;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1066
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1067
  if (!_pdu_info_helper(
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1068
          data,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1069
          end,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1070
          bser_version_out,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1071
          bser_capabilities_out,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1072
          &expected_len,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1073
          &position)) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1074
    return 0;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1075
  }
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1076
  *total_len_out = (int64_t)(expected_len + position);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1077
  return 1;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1078
}
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1079
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1080
// Expected use case is to read a packet from the socket and then call
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1081
// bser.pdu_info on the packet.  It returns the BSER version, BSER capabilities,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1082
// and the total length of the entire response that the peer is sending,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1083
// including the bytes already received. This allows the client  to compute the
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1084
// data size it needs to read before it can decode the data.
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1085
static PyObject* bser_pdu_info(PyObject* self, PyObject* args) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1086
  uint32_t version, capabilities;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1087
  int64_t total_len;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1088
  if (!pdu_info_helper(self, args, &version, &capabilities, &total_len)) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1089
    return NULL;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1090
  }
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1091
  return Py_BuildValue("kkL", version, capabilities, total_len);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1092
}
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1093
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1094
static PyObject* bser_pdu_len(PyObject* self, PyObject* args) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1095
  uint32_t version, capabilities;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1096
  int64_t total_len;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1097
  if (!pdu_info_helper(self, args, &version, &capabilities, &total_len)) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1098
    return NULL;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1099
  }
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1100
  return Py_BuildValue("L", total_len);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1101
}
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1102
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1103
static PyObject* bser_loads(PyObject* self, PyObject* args, PyObject* kw) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1104
  const char* data = NULL;
48411
5140461ee947 fsmonitor: incorporate fixes for Python 3.10 (issue6612)
Raphaël Gomès <rgomes@octobus.net>
parents: 43394
diff changeset
  1105
  Py_ssize_t datalen = 0;
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1106
  const char* start;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1107
  const char* end;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1108
  int64_t expected_len;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1109
  off_t position;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1110
  PyObject* mutable_obj = NULL;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1111
  const char* value_encoding = NULL;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1112
  const char* value_errors = NULL;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1113
  unser_ctx_t ctx = {1, 0};
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1114
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1115
  static char* kw_list[] = {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1116
      "buf", "mutable", "value_encoding", "value_errors", NULL};
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1117
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1118
  if (!PyArg_ParseTupleAndKeywords(
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1119
          args,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1120
          kw,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1121
          "s#|Ozz:loads",
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1122
          kw_list,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1123
          &start,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1124
          &datalen,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1125
          &mutable_obj,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1126
          &value_encoding,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1127
          &value_errors)) {
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1128
    return NULL;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1129
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1130
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1131
  if (mutable_obj) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1132
    ctx.mutable = PyObject_IsTrue(mutable_obj) > 0 ? 1 : 0;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1133
  }
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1134
  ctx.value_encoding = value_encoding;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1135
  if (value_encoding == NULL) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1136
    ctx.value_errors = NULL;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1137
  } else if (value_errors == NULL) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1138
    ctx.value_errors = "strict";
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1139
  } else {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1140
    ctx.value_errors = value_errors;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1141
  }
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1142
  data = start;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1143
  end = data + datalen;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1144
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1145
  if (!_pdu_info_helper(
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1146
          data,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1147
          end,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1148
          &ctx.bser_version,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1149
          &ctx.bser_capabilities,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1150
          &expected_len,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1151
          &position)) {
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1152
    return NULL;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1153
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1154
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1155
  data = start + position;
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1156
  // Verify
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1157
  if (expected_len + data != end) {
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1158
    PyErr_SetString(PyExc_ValueError, "bser data len != header len");
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1159
    return NULL;
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1160
  }
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1161
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1162
  return bser_loads_recursive(&data, end, &ctx);
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1163
}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1164
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1165
static PyObject* bser_load(PyObject* self, PyObject* args, PyObject* kw) {
43385
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1166
  PyObject* load;
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1167
  PyObject* load_method;
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1168
  PyObject* string;
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1169
  PyObject* load_method_args;
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1170
  PyObject* load_method_kwargs;
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1171
  PyObject* fp = NULL;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1172
  PyObject* mutable_obj = NULL;
43385
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1173
  PyObject* value_encoding = NULL;
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1174
  PyObject* value_errors = NULL;
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1175
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1176
  static char* kw_list[] = {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1177
      "fp", "mutable", "value_encoding", "value_errors", NULL};
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1178
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1179
  if (!PyArg_ParseTupleAndKeywords(
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1180
          args,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1181
          kw,
43385
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1182
          "O|OOO:load",
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1183
          kw_list,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1184
          &fp,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1185
          &mutable_obj,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1186
          &value_encoding,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1187
          &value_errors)) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1188
    return NULL;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1189
  }
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1190
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1191
  load = PyImport_ImportModule("pywatchman.load");
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1192
  if (load == NULL) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1193
    return NULL;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1194
  }
43385
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1195
  load_method = PyObject_GetAttrString(load, "load");
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1196
  if (load_method == NULL) {
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1197
    return NULL;
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1198
  }
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1199
  // Mandatory method arguments
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1200
  load_method_args = Py_BuildValue("(O)", fp);
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1201
  if (load_method_args == NULL) {
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1202
    return NULL;
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1203
  }
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1204
  // Optional method arguments
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1205
  load_method_kwargs = PyDict_New();
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1206
  if (load_method_kwargs == NULL) {
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1207
    return NULL;
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1208
  }
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1209
  if (mutable_obj) {
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1210
    PyDict_SetItemString(load_method_kwargs, "mutable", mutable_obj);
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1211
  }
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1212
  if (value_encoding) {
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1213
    PyDict_SetItemString(load_method_kwargs, "value_encoding", value_encoding);
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1214
  }
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1215
  if (value_errors) {
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1216
    PyDict_SetItemString(load_method_kwargs, "value_errors", value_errors);
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1217
  }
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1218
  string = PyObject_Call(load_method, load_method_args, load_method_kwargs);
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1219
  Py_DECREF(load_method_kwargs);
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1220
  Py_DECREF(load_method_args);
6469c23a40a2 fsmonitor: refresh pywatchman with upstream
Gregory Szorc <gregory.szorc@gmail.com>
parents: 37594
diff changeset
  1221
  Py_DECREF(load_method);
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1222
  Py_DECREF(load);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1223
  return string;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1224
}
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1225
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1226
// clang-format off
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1227
static PyMethodDef bser_methods[] = {
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1228
  {"loads", (PyCFunction)bser_loads, METH_VARARGS | METH_KEYWORDS,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1229
   "Deserialize string."},
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1230
  {"load", (PyCFunction)bser_load, METH_VARARGS | METH_KEYWORDS,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1231
   "Deserialize a file object"},
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1232
  {"pdu_info", (PyCFunction)bser_pdu_info, METH_VARARGS,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1233
   "Extract PDU information."},
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1234
  {"pdu_len", (PyCFunction)bser_pdu_len, METH_VARARGS,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1235
   "Extract total PDU length."},
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1236
  {"dumps",  (PyCFunction)bser_dumps, METH_VARARGS | METH_KEYWORDS,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1237
   "Serialize string."},
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1238
  {NULL, NULL, 0, NULL}
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1239
};
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1240
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1241
#if PY_MAJOR_VERSION >= 3
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1242
static struct PyModuleDef bser_module = {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1243
  PyModuleDef_HEAD_INIT,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1244
  "bser",
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1245
  "Efficient encoding and decoding of BSER.",
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1246
  -1,
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1247
  bser_methods
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1248
};
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1249
// clang-format on
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1250
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1251
PyMODINIT_FUNC PyInit_bser(void) {
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1252
  PyObject* mod;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1253
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1254
  mod = PyModule_Create(&bser_module);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1255
  PyType_Ready(&bserObjectType);
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1256
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1257
  return mod;
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1258
}
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1259
#else
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1260
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1261
PyMODINIT_FUNC initbser(void) {
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1262
  (void)Py_InitModule("bser", bser_methods);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1263
  PyType_Ready(&bserObjectType);
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1264
}
30656
16f4b341288d fsmonitor: refresh pywatchman to upstream
Zack Hricz <zphricz@fb.com>
parents: 28528
diff changeset
  1265
#endif // PY_MAJOR_VERSION >= 3
28432
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1266
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1267
/* vim:ts=2:sw=2:et:
2377c4ac4eec fsmonitor: dependencies for new experimental extension
Martijn Pieters <mjpieters@fb.com>
parents:
diff changeset
  1268
 */