Systems Programming (XMUT)
Assignment 2: C programming
Resources and links
What To Hand In
Do not rename these files.
This part will test your application of the conceptual knowledge of C fundamentals to solve practical programming tasks. You may only use the Standard C Library to perform the tasks in this part. You must implement the functions in a file named
editor.c
. You are free to implement other functions within this file that you think are needed to fulfil the tasks.
The programming tasks involve the implementation of several basic
text editor operations: insert, delete, replace, etc. An important component of a text editor is the
editing buffer which can be viewed as a one-dimensional array of characters.
You will implement functions to manipulate the contents of the editing buffer:
- for Core (Tasks 1 and 2), you will implement
editor_insert_string
and editor_delete_string
;
- for Completion (Task 3), you will implement
editor_replace_str
; and
- for Challenge, you will implement
editor_view
.
Sample code showing an example of how you can test your code are provided under the files directory in the archive that contains this file.
You should provide appropriate comments to make your source code readable. If your code does not work and there are no comments, you may lose all marks.
Coding Style
You should follow a consistent coding style when writing your source code. Coding style (aka coding standard) refers to the use of appropriate indentation, proper placement of braces, proper formatting of control constructs, and many others. Following a particular coding style consistently will make your source code more readable.
There are many coding standards available (search "C coding style"), but we suggest you consult the
lightweight Linux kernel coding style (see
coding-style). The relevant sections are Sections 1, 2, 3, 4, 6, and 8. Note that you do not have to follow every recommendation you can find in a coding style document, you just have to apply that style consistently.
Task 1: Core [20 Marks]
Implement a function with the prototype
int editor_insert_string(char editing_buffer[], int editing_buflen, const char* to_insert, int pos);
which will insert the string
to_insert
at index
pos
of
editing_buffer
. The size of
editing_buffer
is
editing_buflen
. When a string is inserted at index
pos
, each of the original characters at index
pos
until the end of the buffer must be moved to the right to make room for the characters in to_insert. The last character is thrown out. The function should return 1 if the string insertion occurred, otherwise it should return 0. Ensure that the last character in the buffer is always the null character.
For example, if
editing_buflen
is 16 and the contents of
editing_buffer
are
after executing
int r = editor_insert_string(editing_buffer, 16, "s!", 12);
the value of
r
should be 1 and contents of
editing_buffer
should be
Task 2: Core [25 Marks]
Implement a function with the prototype
int editor_delete_string(char editing_buffer[], int editing_buflen, const char *to_delete, int offset);
which will delete the first occurrence of the string
to_delete
. The search should start from index
offset
of
editing_buffer
. The size of
editing_buffer
is
editing_buflen
. When a string is deleted at index
pos
, each of the original characters at index
pos
until the end of the buffer must be moved by the length of string
to_delete
to the left. Multiple null characters (
'\0'
) might be inserted at the end of the buffer. The function should return
1
if the string deletion occurred, otherwise, it should return
0
.
For example, if
editing_buflen
is 16 and the contents of
editing_buffer
are
after executing
int r = editor_delete_string(editing_buffer, 16, "rld", 9);
the value of
r
should be 1 and the contents of
editing_buffer
should be
Task 3: Completion [15 Marks]
Implement a function with the prototype
int editor_replace_str(char editing_buffer[], int editing_buflen, const char *str, const char *replacement, int offset);
which will replace the first occurrence of the string
str
with
replacement
. The search for the first occurrence should start from index
offset
of
editing_buffer
. The size of
editing_buffer
is
editing_buflen
.
Note: str
and
replacement
are pointers to arrays of characters. You can access each element of the array by its index.
The replacement should not overwrite other contents in the buffer. This means that if
replacement
is longer than
str
, there is a need to move the characters after
str
to the right. Likewise, if
replacement
is shorter than
str
, there is a need to move the characters after
str
to the left. When moving characters to the right, throw out characters that will not fit in the buffer and when moving characters to the left, insert null characters in the vacated positions.
The question mark
?
is a placeholder for a single character. In other words, if
str
is
n?t, it finds the first occurrence of one of these words:
nut,
not, or
net.
If
str
is empty (regardless of the value of
replacement
), no string replacement should occur. If
replacement
is empty, then it deletes the first occurrence of string
str
.
If the replacement text will go beyond the limits of
editing_buffer
, then replacement should only occur until the end of
editing_buffer
.
Ensure that the last character in the buffer is always the null character.
If the string replacement occurred, the function should return the index corresponding to the last letter of
replacement
in
editing_buffer
, otherwise, it should return -1. If the replacement text will go beyond the limits of
editing_buffer
, the function should return
editing_buflen-1
.
For example, if
editing_buflen
is 16 and the contents of
editing_buffer
are
After executing
int r = editor_replace_str(editing_buffer, 16, "W??ld!", "there", 0);
the value of
r
should be 11 (which is the index of the last 'e' in "there") and the contents of
editing_buffer
should be
Another example if
editing_buflen
is 16 and the contents of
editing_buffer
are
After executing
int r = editor_replace_str(editing_buffer, 16, "W??ld!", "NWEN 214!", 0);
the value of
r
should be 15 (which is the index of the last '4' in "NWEN 214!") and the contents of
editing_buffer
should be
Note: "NWEN 214!" will go beyond the limits of
editing_buffer
, then replacement should only occur until the end of
editing_buffer
. The last character in the buffer is also the null character.
Task 4: Challenge [10 Marks]
Implement a function with the prototype
void editor_view(int rows, int cols, char* viewing_buffer, const char editing_buffer[], int editing_buflen, int wrap);
which will copy the contents of the
editing_buffer
to the
viewing_buffer
for display to the user. Note that the
viewing_buffer
is a
two-dimensional array, with dimensions
cols
columns and
rows
rows. Prior to the copying, the function must set every character in the
viewing_buffer
to the null character.
The argument
wrap
controls the behaviour of the copying process from
editing_buffer
to
viewing_buffer
as follows:
- Regardless of the value of
wrap
, whenever a newline character is encountered in editing_buffer
, the text after the newline character is copied to the next row in viewing_buffer
. Note that the newline character is not copied to viewing_buffer
.
- When
wrap
is 0, the text is not wrapped. This means that when the newline character is not encountered before the end of the current row (at column cols-1
), the rest of the text in the editing_buffer
are discarded until a newline is encountered which will cause the rest of the text to be copied to the next row. Note that column cols-1
in viewing_buffer
is never filled and will retain the null character.
- When
wrap
is non-zero, the text must be wrapped. This means that when the newline character is not encountered before the end of the current row (at column cols-1
in viewing_buffer
), the text after is copied to the next row. Note that column cols-1
in viewing_buffer
is never filled and will retain the null character.
The copying process should terminate when a null character in the
editing_buffer
is encountered.
For example, if
editing_buflen
is 48 and the contents of
editing_buffer
are
and
cols
and
rows
are 11 and 8, respectively. After executing
editor_view(8, 11, viewing_buffer, editing_buffer, 48, 0);
the resulting contents of
viewing_buffer
should be
Alternatively, after executing
editor_view(8, 11, viewing_buffer, editing_buffer, 48, 1);
the resulting contents of
viewing_buffer
should be
Marking Criteria for Tasks 1 -- 4:
Criteria |
Weight |
Expectations for Full Marks |
Compilation |
5% |
Compiles without warnings |
Comments |
10% |
Sufficient and appropriate comments |
Code Quality |
15% |
Consistent coding style |
Correctness |
70% |
Handles all test cases correctly |
|
100% |
|