_info (2706B)
1 #include "config.h" 2 #include <stdio.h> 3 #include <string.h> 4 5 /** 6 * tal - compact tree allocator routines (inspired by talloc) 7 * 8 * Tal is a hierarchical allocator; any pointer allocated by tal can 9 * become the parent of another allocation. When you free that parent, 10 * the children (and grandchildren, etc) are automatically freed. 11 * 12 * This allows you to build complex objects based on their lifetimes, eg: 13 * 14 * struct foo *X = tal(NULL, struct foo); 15 * X->val = tal(X, int); 16 * 17 * and the pointer X->val would be a "child" of the tal context "X"; 18 * tal_free(X->val) would free X->val as expected, by tal_free(X) would 19 * free X and X->val. 20 * 21 * With an overhead of approximately 4 pointers per object 22 * (vs. talloc's 12 pointers), it uses dynamic allocation for 23 * destructors and child lists, so those operations can fail. It does 24 * not support talloc's references or failing destructors. 25 * 26 * See Also: 27 * ccan/tal/str (useful string helpers) 28 * 29 * Example: 30 * #include <stdio.h> 31 * #include <err.h> 32 * #include <ccan/tal/tal.h> 33 * 34 * // A structure containing a popened command. 35 * struct command { 36 * FILE *f; 37 * char *command; 38 * }; 39 * 40 * // When struct command is freed, we also want to pclose pipe. 41 * static void close_cmd(struct command *cmd) 42 * { 43 * pclose(cmd->f); 44 * } 45 * 46 * // This function opens a writable pipe to the given command. 47 * static struct command *open_output_cmd(const tal_t *ctx, 48 * const char *a0, const char *a1) 49 * { 50 * struct command *cmd = tal(ctx, struct command); 51 * 52 * if (!cmd) 53 * return NULL; 54 * 55 * // Note that tal/str has helpers to make this much easier! 56 * cmd->command = tal_arrz(cmd, char, strlen(a0) + strlen(a1) + 2); 57 * if (!cmd->command) { 58 * tal_free(cmd); 59 * return NULL; 60 * } 61 * strcat(cmd->command, a0); 62 * strcat(cmd->command, " "); 63 * strcat(cmd->command, a1); 64 * 65 * cmd->f = popen(cmd->command, "w"); 66 * if (!cmd->f) { 67 * tal_free(cmd); 68 * return NULL; 69 * } 70 * tal_add_destructor(cmd, close_cmd); 71 * return cmd; 72 * } 73 * 74 * int main(int argc, char *argv[]) 75 * { 76 * struct command *cmd; 77 * 78 * if (argc != 2) 79 * errx(1, "Usage: %s <command>\n", argv[0]); 80 * 81 * cmd = open_output_cmd(NULL, argv[1], "hello"); 82 * if (!cmd) 83 * err(1, "Running '%s hello'", argv[1]); 84 * fprintf(cmd->f, "This is a test\n"); 85 * tal_free(cmd); 86 * return 0; 87 * } 88 * 89 * License: BSD-MIT 90 */ 91 int main(int argc, char *argv[]) 92 { 93 if (argc != 2) 94 return 1; 95 96 if (strcmp(argv[1], "depends") == 0) { 97 printf("ccan/alignof\n"); 98 printf("ccan/compiler\n"); 99 printf("ccan/likely\n"); 100 printf("ccan/list\n"); 101 printf("ccan/str\n"); 102 printf("ccan/take\n"); 103 printf("ccan/typesafe_cb\n"); 104 return 0; 105 } 106 107 return 1; 108 }