[textformat]: added missing newline when a message opens. (#245)

* [textformat]: added missing newline when a message opens.

* Added tostring() support to Lua that prints to text format.

Also fixed a gnarly bug that this exposed.
pull/13171/head
Joshua Haberman 5 years ago committed by GitHub
parent 3d955e684c
commit 4c6dcc3c6b
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
  1. 1
      BUILD
  2. 5
      tests/bindings/lua/test_upb.lua
  3. 33
      upb/bindings/lua/msg.c
  4. 2
      upb/reflection.c
  5. 9
      upb/textencode.c

@ -656,6 +656,7 @@ cc_library(
],
deps = [
":reflection",
":textformat",
":upb",
"@lua//:liblua",
],

@ -458,6 +458,11 @@ function test_foo()
assert_error_match("lupb.array expected", function () set.file = 1 end)
set = upb.decode(FileDescriptorSet, descriptor)
-- Test that we can at least call this without crashing.
set_textformat = tostring(set)
-- print(set_textformat)
assert_equal(#set.file, 1)
assert_equal(set.file[1].name, "google/protobuf/descriptor.proto")
end

@ -13,6 +13,7 @@
#include "lauxlib.h"
#include "upb/bindings/lua/upb.h"
#include "upb/reflection.h"
#include "upb/textencode.h"
#include "upb/port_def.inc"
@ -887,9 +888,41 @@ static int lupb_msg_newindex(lua_State *L) {
return 1;
}
/**
* lupb_msg_tostring()
*
* Handles:
* tostring(msg)
* print(msg)
* etc.
*/
static int lupb_msg_tostring(lua_State *L) {
upb_msg *msg = lupb_msg_check(L, 1);
const upb_msgdef *m;
char buf[1024];
size_t size;
lua_getiuservalue(L, 1, LUPB_MSGDEF_INDEX);
m = lupb_msgdef_check(L, -1);
size = upb_textencode(msg, m, NULL, 0, buf, sizeof(buf));
if (size < sizeof(buf)) {
lua_pushlstring(L, buf, size);
} else {
char *ptr = malloc(size + 1);
upb_textencode(msg, m, NULL, 0, ptr, size + 1);
lua_pushlstring(L, ptr, size);
free(ptr);
}
return 1;
}
static const struct luaL_Reg lupb_msg_mm[] = {
{"__index", lupb_msg_index},
{"__newindex", lupb_msg_newindex},
{"__tostring", lupb_msg_tostring},
{NULL, NULL}
};

@ -82,7 +82,7 @@ bool upb_msg_has(const upb_msg *msg, const upb_fielddef *f) {
return *oneofcase(msg, field) == field->number;
} else if (field->presence > 0) {
uint32_t hasbit = field->presence;
return *PTR_AT(msg, hasbit / 8, char) | (1 << (hasbit % 8));
return *PTR_AT(msg, hasbit / 8, char) & (1 << (hasbit % 8));
} else {
UPB_ASSERT(field->descriptortype == UPB_DESCRIPTOR_TYPE_MESSAGE ||
field->descriptortype == UPB_DESCRIPTOR_TYPE_GROUP);

@ -21,8 +21,6 @@ typedef struct {
static void txtenc_msg(txtenc *e, const upb_msg *msg, const upb_msgdef *m);
#define CHK(x) do { if (!(x)) { return false; } } while(0)
static void txtenc_putbytes(txtenc *e, const void *data, size_t len) {
size_t have = e->end - e->ptr;
if (UPB_LIKELY(have >= len)) {
@ -159,6 +157,7 @@ static void txtenc_field(txtenc *e, upb_msgval val, const upb_fielddef *f) {
break;
case UPB_TYPE_MESSAGE:
txtenc_putstr(e, "{");
txtenc_endfield(e);
e->indent_depth++;
txtenc_msg(e, val.msg_val, upb_fielddef_msgsubdef(f));
e->indent_depth--;
@ -224,6 +223,8 @@ static void txtenc_map(txtenc *e, const upb_map *map, const upb_fielddef *f) {
}
}
#define CHK(x) do { if (!(x)) { return false; } } while(0)
static const char *txtenc_parsevarint(const char *ptr, const char *limit,
uint64_t *val) {
uint8_t byte;
@ -333,6 +334,8 @@ static const char *txtenc_unknown(txtenc *e, const char *ptr, const char *end,
return groupnum == -1 ? ptr : NULL;
}
#undef CHK
static void txtenc_msg(txtenc *e, const upb_msg *msg,
const upb_msgdef *m) {
size_t iter = UPB_MSG_BEGIN;
@ -389,5 +392,3 @@ size_t upb_textencode(const upb_msg *msg, const upb_msgdef *m,
txtenc_msg(&e, msg, m);
return txtenc_nullz(&e, size);
}
#undef CHK

Loading…
Cancel
Save