ref-filter: free item->value and item->value->s
Release item->value. Initialize item->value->s dynamically and then release its resources. Release some local variables. Final goal of this patch is to reduce number of memory leaks. Signed-off-by: Olga Telezhnaia <olyatelezhnaya@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
Olga Telezhnaya committed
Oct 18, 2018 at 07:28 UTC
f0062d3b74cfd4425188e16cbda358b1e0228d85
1 file changed
+54
-42
ref-filter.c
+54
-42
@@ -875,7 +875,7 @@ static void grab_common_values(struct atom_value *val, int deref, struct expand_
875
if (deref)
876
name++;
877
if (!strcmp(name, "objecttype"))
878
- v->s = type_name(oi->type);
878
+ v->s = xstrdup(type_name(oi->type));
879
else if (!strcmp(name, "objectsize")) {
880
v->value = oi->size;
881
v->s = xstrfmt("%lu", oi->size);
@@ -899,9 +899,9 @@ static void grab_tag_values(struct atom_value *val, int deref, struct object *ob
899
if (deref)
900
name++;
901
if (!strcmp(name, "tag"))
902
- v->s = tag->tag;
902
+ v->s = xstrdup(tag->tag);
903
else if (!strcmp(name, "type") && tag->tagged)
904
- v->s = type_name(tag->tagged->type);
904
+ v->s = xstrdup(type_name(tag->tagged->type));
905
else if (!strcmp(name, "object") && tag->tagged)
906
v->s = xstrdup(oid_to_hex(&tag->tagged->oid));
907
}
@@ -1032,7 +1032,7 @@ static void grab_date(const char *buf, struct atom_value *v, const char *atomnam
1032
v->value = timestamp;
1033
return;
1034
bad:
1035
- v->s = "";
1035
+ v->s = xstrdup("");
1036
v->value = 0;
1037
}
1038
@@ -1227,7 +1227,7 @@ static void fill_missing_values(struct atom_value *val)
1227
for (i = 0; i < used_atom_cnt; i++) {
1228
struct atom_value *v = &val[i];
1229
if (v->s == NULL)
1230
- v->s = "";
1230
+ v->s = xstrdup("");
1231
}
1232
}
1233
@@ -1273,7 +1273,8 @@ static inline char *copy_advance(char *dst, const char *src)
1273
static const char *lstrip_ref_components(const char *refname, int len)
1274
{
1275
long remaining = len;
1276
- const char *start = refname;
1276
+ const char *start = xstrdup(refname);
1277
+ const char *to_free = start;
1278
1279
if (len < 0) {
1280
int i;
@@ -1294,20 +1295,24 @@ static const char *lstrip_ref_components(const char *refname, int len)
1295
while (remaining > 0) {
1296
switch (*start++) {
1297
case '\0':
1297
- return "";
1298
+ free((char *)to_free);
1299
+ return xstrdup("");
1300
case '/':
1301
remaining--;
1302
break;
1303
}
1304
}
1305
1306
+ start = xstrdup(start);
1307
+ free((char *)to_free);
1308
return start;
1309
}
1310
1311
static const char *rstrip_ref_components(const char *refname, int len)
1312
{
1313
long remaining = len;
1310
- char *start = xstrdup(refname);
1314
+ const char *start = xstrdup(refname);
1315
+ const char *to_free = start;
1316
1317
if (len < 0) {
1318
int i;
@@ -1327,9 +1332,10 @@ static const char *rstrip_ref_components(const char *refname, int len)
1332
1333
while (remaining-- > 0) {
1334
char *p = strrchr(start, '/');
1330
- if (p == NULL)
1331
- return "";
1332
- else
1335
+ if (p == NULL) {
1336
+ free((char *)to_free);
1337
+ return xstrdup("");
1338
+ } else
1339
p[0] = '\0';
1340
}
1341
return start;
@@ -1344,7 +1350,7 @@ static const char *show_ref(struct refname_atom *atom, const char *refname)
1350
else if (atom->option == R_RSTRIP)
1351
return rstrip_ref_components(refname, atom->rstrip);
1352
else
1347
- return refname;
1353
+ return xstrdup(refname);
1354
}
1355
1356
static void fill_remote_ref_details(struct used_atom *atom, const char *refname,
@@ -1358,7 +1364,7 @@ static void fill_remote_ref_details(struct used_atom *atom, const char *refname,
1364
NULL, AHEAD_BEHIND_FULL) < 0) {
1365
*s = xstrdup(msgs.gone);
1366
} else if (!num_ours && !num_theirs)
1361
- *s = "";
1367
+ *s = xstrdup("");
1368
else if (!num_ours)
1369
*s = xstrfmt(msgs.behind, num_theirs);
1370
else if (!num_theirs)
@@ -1373,36 +1379,31 @@ static void fill_remote_ref_details(struct used_atom *atom, const char *refname,
1379
}
1380
} else if (atom->u.remote_ref.option == RR_TRACKSHORT) {
1381
if (stat_tracking_info(branch, &num_ours, &num_theirs,
1376
- NULL, AHEAD_BEHIND_FULL) < 0)
1382
+ NULL, AHEAD_BEHIND_FULL) < 0) {
1383
+ *s = xstrdup("");
1384
return;
1378
-
1385
+ }
1386
if (!num_ours && !num_theirs)
1380
- *s = "=";
1387
+ *s = xstrdup("=");
1388
else if (!num_ours)
1382
- *s = "<";
1389
+ *s = xstrdup("<");
1390
else if (!num_theirs)
1384
- *s = ">";
1391
+ *s = xstrdup(">");
1392
else
1386
- *s = "<>";
1393
+ *s = xstrdup("<>");
1394
} else if (atom->u.remote_ref.option == RR_REMOTE_NAME) {
1395
int explicit;
1396
const char *remote = atom->u.remote_ref.push ?
1397
pushremote_for_branch(branch, &explicit) :
1398
remote_for_branch(branch, &explicit);
1392
- if (explicit)
1393
- *s = xstrdup(remote);
1394
- else
1395
- *s = "";
1399
+ *s = xstrdup(explicit ? remote : "");
1400
} else if (atom->u.remote_ref.option == RR_REMOTE_REF) {
1401
int explicit;
1402
const char *merge;
1403
1404
merge = remote_ref_for_branch(branch, atom->u.remote_ref.push,
1405
&explicit);
1402
- if (explicit)
1403
- *s = xstrdup(merge);
1404
- else
1405
- *s = "";
1406
+ *s = xstrdup(explicit ? merge : "");
1407
} else
1408
BUG("unhandled RR_* enum");
1409
}
@@ -1451,7 +1452,7 @@ char *get_head_description(void)
1452
static const char *get_symref(struct used_atom *atom, struct ref_array_item *ref)
1453
{
1454
if (!ref->symref)
1454
- return "";
1455
+ return xstrdup("");
1456
else
1457
return show_ref(&atom->u.refname, ref->symref);
1458
}
@@ -1510,7 +1511,7 @@ static int populate_value(struct ref_array_item *ref, struct strbuf *err)
1511
ref->symref = resolve_refdup(ref->refname, RESOLVE_REF_READING,
1512
NULL, NULL);
1513
if (!ref->symref)
1513
- ref->symref = "";
1514
+ ref->symref = xstrdup("");
1515
}
1516
1517
/* Fill in specials first */
@@ -1536,20 +1537,23 @@ static int populate_value(struct ref_array_item *ref, struct strbuf *err)
1537
refname = get_symref(atom, ref);
1538
else if (starts_with(name, "upstream")) {
1539
const char *branch_name;
1539
- v->s = "";
1540
/* only local branches may have an upstream */
1541
if (!skip_prefix(ref->refname, "refs/heads/",
1542
- &branch_name))
1542
+ &branch_name)) {
1543
+ v->s = xstrdup("");
1544
continue;
1545
+ }
1546
branch = branch_get(branch_name);
1547
1548
refname = branch_get_upstream(branch, NULL);
1549
if (refname)
1550
fill_remote_ref_details(atom, refname, branch, &v->s);
1551
+ else
1552
+ v->s = xstrdup("");
1553
continue;
1554
} else if (atom->u.remote_ref.push) {
1555
const char *branch_name;
1552
- v->s = "";
1556
+ v->s = xstrdup("");
1557
if (!skip_prefix(ref->refname, "refs/heads/",
1558
&branch_name))
1559
continue;
@@ -1562,10 +1566,12 @@ static int populate_value(struct ref_array_item *ref, struct strbuf *err)
1566
if (!refname)
1567
continue;
1568
}
1569
+ /* We will definitely re-init v->s on the next line. */
1570
+ free((char *)v->s);
1571
fill_remote_ref_details(atom, refname, branch, &v->s);
1572
continue;
1573
} else if (starts_with(name, "color:")) {
1568
- v->s = atom->u.color;
1574
+ v->s = xstrdup(atom->u.color);
1575
continue;
1576
} else if (!strcmp(name, "flag")) {
1577
char buf[256], *cp = buf;
@@ -1574,7 +1580,7 @@ static int populate_value(struct ref_array_item *ref, struct strbuf *err)
1580
if (ref->flag & REF_ISPACKED)
1581
cp = copy_advance(cp, ",packed");
1582
if (cp == buf)
1577
- v->s = "";
1583
+ v->s = xstrdup("");
1584
else {
1585
*cp = '\0';
1586
v->s = xstrdup(buf + 1);
@@ -1584,40 +1590,42 @@ static int populate_value(struct ref_array_item *ref, struct strbuf *err)
1590
continue;
1591
} else if (!strcmp(name, "HEAD")) {
1592
if (atom->u.head && !strcmp(ref->refname, atom->u.head))
1587
- v->s = "*";
1593
+ v->s = xstrdup("*");
1594
else
1589
- v->s = " ";
1595
+ v->s = xstrdup(" ");
1596
continue;
1597
} else if (starts_with(name, "align")) {
1598
v->handler = align_atom_handler;
1593
- v->s = "";
1599
+ v->s = xstrdup("");
1600
continue;
1601
} else if (!strcmp(name, "end")) {
1602
v->handler = end_atom_handler;
1597
- v->s = "";
1603
+ v->s = xstrdup("");
1604
continue;
1605
} else if (starts_with(name, "if")) {
1606
const char *s;
1601
- v->s = "";
1607
if (skip_prefix(name, "if:", &s))
1608
v->s = xstrdup(s);
1609
+ else
1610
+ v->s = xstrdup("");
1611
v->handler = if_atom_handler;
1612
continue;
1613
} else if (!strcmp(name, "then")) {
1614
v->handler = then_atom_handler;
1608
- v->s = "";
1615
+ v->s = xstrdup("");
1616
continue;
1617
} else if (!strcmp(name, "else")) {
1618
v->handler = else_atom_handler;
1612
- v->s = "";
1619
+ v->s = xstrdup("");
1620
continue;
1621
} else
1622
continue;
1623
1624
if (!deref)
1618
- v->s = refname;
1625
+ v->s = xstrdup(refname);
1626
else
1627
v->s = xstrfmt("%s^{}", refname);
1628
+ free((char *)refname);
1629
}
1630
1631
for (i = 0; i < used_atom_cnt; i++) {
@@ -1988,6 +1996,10 @@ static int ref_filter_handler(const char *refname, const struct object_id *oid,
1996
static void free_array_item(struct ref_array_item *item)
1997
{
1998
free((char *)item->symref);
1999
+ if (item->value) {
2000
+ free((char *)item->value->s);
2001
+ free(item->value);
2002
+ }
2003
free(item);
2004
}
2005