1
0
mirror of https://github.com/cc65/cc65.git synced 2025-08-08 06:25:17 +00:00

Merge pull request #670 from greg-king5/string-pointer-break

Fix strpbrk() problems.
This commit is contained in:
Oliver Schmidt
2018-06-01 13:15:52 +02:00
committed by GitHub
4 changed files with 88 additions and 39 deletions

View File

@@ -4,7 +4,7 @@
<title>cc65 function reference <title>cc65 function reference
<author><url url="mailto:uz@cc65.org" name="Ullrich von Bassewitz">,<newline> <author><url url="mailto:uz@cc65.org" name="Ullrich von Bassewitz">,<newline>
<url url="mailto:greg.king5@verizon.net" name="Greg King"> <url url="mailto:greg.king5@verizon.net" name="Greg King">
<date>2018-05-23 <date>2018-05-29
<abstract> <abstract>
cc65 is a C compiler for 6502 based systems. This function reference describes cc65 is a C compiler for 6502 based systems. This function reference describes
@@ -717,6 +717,7 @@ communication, see also <tt>testcode/lib/ser-test.c</tt>.
<item><ref id="strncmp" name="strncmp"> <item><ref id="strncmp" name="strncmp">
<item><ref id="strncpy" name="strncpy"> <item><ref id="strncpy" name="strncpy">
<item><ref id="strnicmp" name="strnicmp"> <item><ref id="strnicmp" name="strnicmp">
<item><ref id="strpbrk" name="strpbrk">
<item><ref id="strqtok" name="strqtok"> <item><ref id="strqtok" name="strqtok">
<item><ref id="strrchr" name="strrchr"> <item><ref id="strrchr" name="strrchr">
<item><ref id="strspn" name="strspn"> <item><ref id="strspn" name="strspn">
@@ -6802,6 +6803,7 @@ be used in presence of a prototype.
</itemize> </itemize>
<tag/Availability/ISO 9899 <tag/Availability/ISO 9899
<tag/See also/ <tag/See also/
<ref id="strpbrk" name="strpbrk">,
<ref id="strqtok" name="strqtok">, <ref id="strqtok" name="strqtok">,
<ref id="strspn" name="strspn">, <ref id="strspn" name="strspn">,
<ref id="strstr" name="strstr">, <ref id="strstr" name="strstr">,
@@ -7092,6 +7094,32 @@ be used in presence of a prototype.
</quote> </quote>
<sect1>strpbrk<label id="strpbrk"><p>
<quote>
<descrip>
<tag/Function/Find a character in a string, from a set of characters.
<tag/Header/<tt/<ref id="string.h" name="string.h">/
<tag/Declaration/<tt/char* __fastcall__ strpbrk (const char* str, const char* set);/
<tag/Description/<tt/strpbrk()/ searches within <tt/str/ for the first
occurance of any character from <tt/set/. It returns a pointer to that
character if found; otherwise, it returns <tt/NULL/.
<tag/Notes/<itemize>
<item>The function is available only as a fastcall function;
so, it should be used only in the presence of a prototype.
</itemize>
<tag/Availability/ISO 9899
<tag/See also/
<ref id="strchr" name="strchr">,
<ref id="strcspn" name="strcspn">,
<ref id="strqtok" name="strqtok">,
<ref id="strspn" name="strspn">,
<ref id="strtok" name="strtok">
<tag/Example/None.
</descrip>
</quote>
<sect1>strqtok<label id="strqtok"><p> <sect1>strqtok<label id="strqtok"><p>
<quote> <quote>
@@ -7116,7 +7144,7 @@ a second <tt/s1/ string before it finishes the first one.
<tag/Availability/cc65 <tag/Availability/cc65
<tag/See also/ <tag/See also/
<ref id="strcspn" name="strcspn">, <ref id="strcspn" name="strcspn">,
<!-- <ref id="strpbrk" name="strpbrk">, --> <ref id="strpbrk" name="strpbrk">,
<ref id="strspn" name="strspn">, <ref id="strspn" name="strspn">,
<ref id="strtok" name="strtok"> <ref id="strtok" name="strtok">
<tag/Example/None. <tag/Example/None.
@@ -7164,6 +7192,7 @@ be used in presence of a prototype.
<tag/Availability/ISO 9899 <tag/Availability/ISO 9899
<tag/See also/ <tag/See also/
<ref id="strcspn" name="strcspn">, <ref id="strcspn" name="strcspn">,
<ref id="strpbrk" name="strpbrk">,
<ref id="strstr" name="strstr"> <ref id="strstr" name="strstr">
<tag/Example/None. <tag/Example/None.
</descrip> </descrip>
@@ -7216,7 +7245,7 @@ a second <tt/s1/ string before it finishes the first one.
<tag/Availability/ISO 9899 <tag/Availability/ISO 9899
<tag/See also/ <tag/See also/
<ref id="strcspn" name="strcspn">, <ref id="strcspn" name="strcspn">,
<!-- <ref id="strpbrk" name="strpbrk">, --> <ref id="strpbrk" name="strpbrk">,
<ref id="strqtok" name="strqtok">, <ref id="strqtok" name="strqtok">,
<ref id="strspn" name="strspn"> <ref id="strspn" name="strspn">
<tag/Example/None. <tag/Example/None.

View File

@@ -53,6 +53,7 @@ size_t __fastcall__ strlen (const char* s);
char* __fastcall__ strncat (char* s1, const char* s2, size_t count); char* __fastcall__ strncat (char* s1, const char* s2, size_t count);
int __fastcall__ strncmp (const char* s1, const char* s2, size_t count); int __fastcall__ strncmp (const char* s1, const char* s2, size_t count);
char* __fastcall__ strncpy (char* dest, const char* src, size_t count); char* __fastcall__ strncpy (char* dest, const char* src, size_t count);
char* __fastcall__ strpbrk (const char* str, const char* set);
char* __fastcall__ strrchr (const char* s, int c); char* __fastcall__ strrchr (const char* s, int c);
size_t __fastcall__ strspn (const char* s1, const char* s2); size_t __fastcall__ strspn (const char* s1, const char* s2);
char* __fastcall__ strstr (const char* str, const char* substr); char* __fastcall__ strstr (const char* str, const char* substr);

View File

@@ -1,60 +1,53 @@
;
; Ullrich von Bassewitz, 11.06.1998
; ;
; char* strpbrk (const char* s1, const char* s2); ; 1998-06-11, Ullrich von Bassewitz
; 2018-05-29, Greg King
;
; char* __fastcall__ strpbrk (const char* str, const char* set);
; ;
.export _strpbrk .export _strpbrk
.import popax, return0
.importzp ptr1, ptr2, tmp1, tmp2, tmp3 .import popax
.importzp ptr1, ptr2, tmp2, tmp3
_strpbrk: _strpbrk:
jsr popax ; get s2 sta ptr2 ; store set
sta ptr2
stx ptr2+1 stx ptr2+1
jsr popax ; get s1 jsr popax
sta ptr1 stx ptr1+1 ; store str's high byte
stx ptr1+1 ldx #<$0000
ldy #$00 stx ptr1
tay ; use str's low byte as index
L1: lda (ptr1),y ; get next char from s1 L1: lda (ptr1),y ; get next char from str
beq L9 ; jump if done beq L9 ; jump if done
sta tmp2 ; save char sta tmp2 ; save char
iny sty tmp3 ; save index into str
bne L2
inc ptr1+1
L2: sty tmp3 ; save index into s1
ldy #0 ; get index into s2 ldy #$00
L3: lda (ptr2),y ; L3: lda (ptr2),y ; look at each char in set
beq L4 ; jump if done beq L4 ; jump if done
cmp tmp2 cmp tmp2
beq L6 beq L6 ; break out of loops if something found
iny iny
bne L3 bne L3
; The character was not found in s2. Increment the counter and start over ; The character was not found in set. Increment the counter; and start over.
L4: ldy tmp3 ; reload index L4: ldy tmp3 ; reload index
inx iny
bne L1
inc tmp1
bne L1 bne L1
inc ptr1+1
bne L1 ; branch always
; A character was found. Calculate a pointer to this char in s1 and return it. ; A character was found. Return its str pointer.
L6: ldx ptr1+1 L6: ldx ptr1+1
lda tmp3 ; get y offset lda tmp3 ; get .Y offset
clc rts
adc ptr1
bcc L7
inx
L7: rts
; None of the characters in s2 was found - return NULL
L9: jmp return0
; None of the characters in set was found -- return NULL.
L9: ;ldx #>$0000 ; (set by prolog)
;lda #<$0000 ; (set by '\0' at end of str)
rts

View File

@@ -0,0 +1,26 @@
#include <stdio.h>
#include <string.h>
static const char fox[] = "The quick brown fox jumped over the lazy dogs.";
void main (void)
{
printf ("Testing strpbrk():\n");
if (strpbrk (fox, "qwerty") != &fox[2]) {
printf ("\nThe first 'e' wasn't found.\n");
}
if (strpbrk (fox, "QWERTY") != &fox[0]) {
printf ("The 'T' wasn't found.\n");
}
if (strpbrk (fox, "asdfg") != &fox[16]) {
printf ("The 'f' wasn't found.\n");
}
if (strpbrk (fox, "nxv,zmb") != &fox[10]) {
printf ("The 'b' wasn't found.\n");
}
if (strpbrk (fox, "!@#$%^&*()-+=[];:',/?<>.") != &fox[45]) {
printf ("The '.' wasn't found.\n");
}
printf ("\nFinished.\n");
}