Skip to content

Commit 25cad90

Browse files
committed
glib: Micro-optimize GStringBuilder construction to have fewer function calls
1 parent 6e76ebb commit 25cad90

File tree

1 file changed

+16
-12
lines changed

1 file changed

+16
-12
lines changed

glib/src/gstring_builder.rs

Lines changed: 16 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -21,20 +21,25 @@ wrapper! {
2121
copy => |ptr| ffi::g_string_new((*ptr).str),
2222
free => |ptr| ffi::g_string_free(ptr, ffi::GTRUE),
2323
init => |ptr| unsafe {
24-
*ptr = ffi::GString {
25-
str: ffi::g_malloc0(64) as *mut _,
24+
let inner = ffi::GString {
25+
str: ffi::g_malloc(64) as *mut _,
2626
len: 0,
2727
allocated_len: 64,
2828
};
29+
ptr::write(inner.str, 0);
30+
31+
*ptr = inner;
2932
},
3033
copy_into => |dest, src| {
34+
assert!((*src).allocated_len > (*src).len);
3135
let allocated_len = (*src).allocated_len;
32-
let mut inner = ffi::GString {
33-
str: ffi::g_malloc0(allocated_len) as *mut _,
36+
let inner = ffi::GString {
37+
str: ffi::g_malloc(allocated_len) as *mut _,
3438
len: 0,
3539
allocated_len,
3640
};
37-
ffi::g_string_append_len(&mut inner, (*src).str, (*src).len as isize);
41+
// +1 to also copy the NUL-terminator
42+
ptr::copy_nonoverlapping((*src).str, inner.str, (*src).len + 1);
3843
*dest = inner;
3944
},
4045
clear => |ptr| {
@@ -56,19 +61,16 @@ impl GStringBuilder {
5661
let allocated_len = usize::next_power_of_two(std::cmp::max(data.len(), 64) + 1);
5762
assert_ne!(allocated_len, 0);
5863

59-
let mut inner = ffi::GString {
64+
let inner = ffi::GString {
6065
str: ffi::g_malloc(allocated_len) as *mut _,
61-
len: 0,
66+
len: data.len(),
6267
allocated_len,
6368
};
6469
if data.is_empty() {
6570
ptr::write(inner.str, 0);
6671
} else {
67-
ffi::g_string_append_len(
68-
&mut inner,
69-
data.as_ptr() as *const _,
70-
data.len() as isize,
71-
);
72+
ptr::copy_nonoverlapping(data.as_ptr() as *const _, inner.str, data.len());
73+
ptr::write(inner.str.add(data.len()), 0);
7274
}
7375
Self { inner }
7476
}
@@ -249,6 +251,7 @@ mod tests {
249251
#[test]
250252
fn append() {
251253
let mut s = crate::GStringBuilder::new("");
254+
assert_eq!(&*s, "");
252255
s.append("Hello");
253256
s.append(" ");
254257
s.append("there!");
@@ -259,6 +262,7 @@ mod tests {
259262
#[test]
260263
fn prepend() {
261264
let mut s = crate::GStringBuilder::new("456");
265+
assert_eq!(&*s, "456");
262266
s.prepend("123");
263267
assert_eq!(&*s, "123456");
264268
}

0 commit comments

Comments
 (0)