From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.2 (2018-09-13) on dcvr.yhbt.net X-Spam-Level: X-Spam-ASN: X-Spam-Status: No, score=-3.2 required=3.0 tests=ALL_TRUSTED,AWL,BAYES_00 shortcircuit=no autolearn=ham autolearn_force=no version=3.4.2 Received: from localhost (dcvr.yhbt.net [127.0.0.1]) by dcvr.yhbt.net (Postfix) with ESMTP id AB70A211B4 for ; Sat, 1 Dec 2018 13:31:26 +0000 (UTC) From: Eric Wong To: kcar-public@bogomips.org Subject: [PATCH 01/11] introduce new str_new_dd_freeze internal function Date: Sat, 1 Dec 2018 13:31:15 +0000 Message-Id: <20181201133125.5524-2-e@80x24.org> In-Reply-To: <20181201133125.5524-1-e@80x24.org> References: <20181201133125.5524-1-e@80x24.org> List-Id: This seems like it will be a common pattern to create and immediately dedupe a string. In the future, we may be able to save some memory by eliding temporary object creation or releasing heap memory via rb_str_resize(..., 0) --- ext/kcar/extconf.rb | 15 ++++++++++----- ext/kcar/kcar.rl | 9 +++++++-- 2 files changed, 17 insertions(+), 7 deletions(-) diff --git a/ext/kcar/extconf.rb b/ext/kcar/extconf.rb index 89ac586..b65846a 100644 --- a/ext/kcar/extconf.rb +++ b/ext/kcar/extconf.rb @@ -6,15 +6,20 @@ dir_config("kcar") have_macro("SIZEOF_OFF_T", "ruby.h") or check_sizeof("off_t", "sys/types.h") have_macro("SIZEOF_LONG", "ruby.h") or check_sizeof("long", "sys/types.h") -uminus_dedupe = false +message('checking if String#-@ (str_uminus) dedupes... ') begin - # oddly, opt_str_freeze is not always effective: - # https://bugs.ruby-lang.org/issues/13282 a = -(%w(t e s t).join) b = -(%w(t e s t).join) - uminus_dedupe = a.object_id == b.object_id + if a.equal?(b) + $CPPFLAGS += " -DSTR_UMINUS_DEDUPE=1 " + message("yes\n") + else + $CPPFLAGS += " -DSTR_UMINUS_DEDUPE=0 " + message("no, needs Ruby 2.5+\n") + end rescue NoMethodError + $CPPFLAGS += " -DSTR_UMINUS_DEDUPE=0 " + message("no, String#-@ not available\n") end -$CFLAGS += " -DSTR_UMINUS_DEDUPE=#{uminus_dedupe ? 1 : 0}" create_makefile("kcar_ext") diff --git a/ext/kcar/kcar.rl b/ext/kcar/kcar.rl index cbcfa97..79f65db 100644 --- a/ext/kcar/kcar.rl +++ b/ext/kcar/kcar.rl @@ -106,6 +106,11 @@ static VALUE str_dd_freeze(VALUE str) return str; } +static VALUE str_new_dd_freeze(const char *ptr, long len) +{ + return str_dd_freeze(rb_str_new(ptr, len)); +} + static VALUE stripped_str_new(const char *str, long len) { long end; @@ -161,7 +166,7 @@ status_phrase(struct http_parser *hp, VALUE hdr, const char *ptr, size_t len) { long nr; - hp->status = str_dd_freeze(rb_str_new(ptr, len)); + hp->status = str_new_dd_freeze(ptr, len); /* RSTRING_PTR is null terminated, ptr is not */ nr = strtol(RSTRING_PTR(hp->status), NULL, 10); @@ -238,7 +243,7 @@ static void write_value(VALUE hdr, struct http_parser *hp, vlen = LEN(mark, p); VALIDATE_MAX_LENGTH(vlen, FIELD_VALUE); VALIDATE_MAX_LENGTH(flen, FIELD_NAME); - f = str_dd_freeze(rb_str_new(fptr, (long)flen)); + f = str_new_dd_freeze(fptr, (long)flen); v = stripped_str_new(vptr, (long)vlen); /* needs more tests for error-checking here */