{"id":3886,"date":"2019-12-14T00:01:49","date_gmt":"2019-12-14T08:01:49","guid":{"rendered":"https:\/\/c-for-dummies.com\/blog\/?p=3886"},"modified":"2019-12-07T10:01:20","modified_gmt":"2019-12-07T18:01:20","slug":"my-own-strlcpy-function","status":"publish","type":"post","link":"https:\/\/c-for-dummies.com\/blog\/?p=3886","title":{"rendered":"My Own <em>strlcpy()<\/em> Function"},"content":{"rendered":"<p>Armed with information about how the non-standard <em>strlcpy()<\/em> function is implemented by my compiler (see <a href=\"https:\/\/c-for-dummies.com\/blog\/?p=3873\">last week&#8217;s Lesson<\/a>), and fully testing its input and output, I was better able to craft my own version. Granted, it&#8217;s not the way I would have coded things on my own, but the point is to recreate the function exactly so it can be used as a substitute.<br \/>\n<!--more--><br \/>\nHere is my reverse-engineered solution to the <em>strlcpy()<\/em> function, which includes the <em>main()<\/em> and <em>test()<\/em> functions from last week&#8217;s sample code:<\/p>\n<pre class=\"screen\">\r\n#include &lt;stdio.h&gt;\r\n\r\nsize_t strlcpy(char *restrict dst, const char *restrict src, size_t dstsize)\r\n{\r\n    int offset;\r\n\r\n    <span class=\"comments\">\/* duplicate the string up to dstsize *\/<\/span>\r\n    offset = 0;\r\n        <span class=\"comments\">\/* guard against silly dstsize values *\/<\/span>\r\n    if( dstsize &gt; 0 )\r\n    {\r\n        while( *(src+offset) != '\\0' )\r\n        {\r\n            <span class=\"comments\">\/* bail if dstsize is met *\/<\/span>\r\n            if( offset==dstsize )\r\n            {\r\n                offset--;\r\n                break;\r\n            }\r\n\r\n            <span class=\"comments\">\/* duplicate the string *\/<\/span>\r\n            *(dst+offset) = *(src+offset);\r\n            offset++;\r\n        }\r\n    }\r\n    <span class=\"comments\">\/* always remember to cap a created string! *\/<\/span>\r\n    *(dst+offset) = '\\0';\r\n    \r\n    <span class=\"comments\">\/* return the string length of src *\/<\/span>\r\n    while( *(src+offset) != '\\0' )\r\n        offset++;\r\n\r\n    return(offset);\r\n}\r\n\r\nvoid test(int size)\r\n{\r\n    char string[] = \"Hello there, Venus\";\r\n    char buffer[19];\r\n    int r;\r\n\r\n    r = strlcpy(buffer,string,size);\r\n\r\n    printf(\"Copied '%s' into '%s', length %d\\n\",\r\n            string,\r\n            buffer,\r\n            r\r\n          );\r\n}\r\n\r\nint main()\r\n{\r\n    test(19);\r\n    test(10);\r\n    test(1);\r\n    test(0);\r\n\r\n    return(0);\r\n}<\/pre>\n<p>My <em>strlcpy()<\/em> function uses <em>int<\/em> variable <code>offset<\/code> to track copying from <code>src<\/code> to <code>dst<\/code>. An <em>if<\/em> test immediately determines whether the <code>dstsize<\/code> value is valid:<\/p>\n<p><code>if( dstsize &gt; 0 )<\/code><\/p>\n<p>If not, the <code>dst<\/code> string is capped (a must) at Line 27:<\/p>\n<p><code>*(dst+offset) = '\\0';<\/code><\/p>\n<p>When the <code>dstsize<\/code> value is legitimate (greater than zero) a <em>while<\/em> loop at Line 12 copies the characters from <code>src<\/code> to <code>dst<\/code>. Line 15 ensures that only <code>dstsize<\/code> characters (or fewer) are copied. Copying takes place at Line 22. And the <code>offset<\/code> variable is incremented at Line 23.<\/p>\n<p>The final <em>while<\/em> loop at Line 30 counts the length of the <code>scr<\/code> string. I couldn&#8217;t use the <em>strlen()<\/em> function because doing so requires including the <code>string.h<\/code> header file. This inclusion results in a slew of warnings and errors because of my <em>strlcpy()<\/em> function and its conflicting definition with <em>strlcpy()<\/em> supplied by the system&#8217;s C library.<\/p>\n<p>My code&#8217;s output matched that of the control program, so I think I&#8217;m good. Had I not cross-checked my version with the one supplied with the compiler, it would have returned different values. In fact, the <em>man<\/em> page for <em>strlcpy()<\/em> contains extensive notes and examples to explain how the return value is used. It&#8217;s interesting information, especially if you are to properly concoct your own, similar &mdash; and compatible &mdash; function.<\/p>\n<p>Next week I tackle the <em>strlcat()<\/em> function.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Crafting my own <em>strlcpy<\/em> function was easier after I studied the original function and ran tests on its operation. <a href=\"https:\/\/c-for-dummies.com\/blog\/?p=3886\">Continue reading <span class=\"meta-nav\">&rarr;<\/span><\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[2],"tags":[],"class_list":["post-3886","post","type-post","status-publish","format-standard","hentry","category-main"],"_links":{"self":[{"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=\/wp\/v2\/posts\/3886","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=3886"}],"version-history":[{"count":7,"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=\/wp\/v2\/posts\/3886\/revisions"}],"predecessor-version":[{"id":3900,"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=\/wp\/v2\/posts\/3886\/revisions\/3900"}],"wp:attachment":[{"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=3886"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=3886"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=3886"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}