F0 - Specification 📐

You will conceive of an idea for a novel character device with the objective of designing something that is creative and non-trivial and will provide for an entertaining demonstration as part of someone's final presentation.

With the knowledge that it is one of your colleagues who will be responsible for actually implementing your idea, you will write a specification of the behavior of each syscall that is precise and detailed enough for them to implement it correctly.

To further guide your colleague in implementing a device that complies with your creative vision, you must write a userspace program that executes a suite of tests that a correct implementation should pass.

For F1, you will randomly be assigned any one of the specifications submitted for F0, including a chance of being assigned your own F0 submission!

Outcomes:

What to submit:

Procedure:

  1. Brainstorm some ideas with an eye for how the behavior can be implemented by a real character device

    1. Some entertaining ideas may be more feasible on paper than in practice

    2. Get started early so that you don't have to pick the first idea you can come up with right before the due date

    3. As a source of inspiration, here are some categories of ideas that have proved viable in the past with examples of what previous students did:

      1. A cipher or code for encrypting and decrypting text e.g. Vigenère or Pig Latin

      2. A simple game, like tic-tac-toe

      3. A tool such as a unit converter

      4. A simulator for some process e.g. ordering food at a drive-thru window, or a Tamagotchi-pet, or interpreting a simple programming language

  2. The most important system calls to figure out will be read(2), write(2) and ioctl(2)

    1. read(2) and write(2) are best at handling strings of text, while if you want to process numbers, ioctl(2) is probably a better option

    2. ioctl(2) can be used as a catch-all mechansim to request some action to be performed

    3. The interface of commands implemented by your ioctl(2) must be defined using the appropriate _IO0. macros and provided to userspace in a header file

  3. Once you have designed the core functionality of the device, consider how those functions will (or will not) interact with the file position value that the kernel stores for each open file and how lseek will fit into that picture

    1. What if any types of repositioning should be supported?

    2. How will the other functions handle a file position that might be out of bounds?

  4. Finally, you have to think about the resource lifecycle within the module.

    1. Is there some persistent state the whole time the module is loaded?

    2. How should device state be initialized at load time in your init() function or when a device file is opened in your open() function?

    3. Correspondingly, what resource cleanup should be performed in your exit() function and release() function?

  5. Write a plain-text specification for the open(2), read(2), write(2), close(2), ioctl(2), and lseek(2) syscalls.

    1. You must describe how a user can correctly invoke each syscall and what behavior or information it accepts and/or returns.

    2. You must describe the behavior and errno values returned for all possible failure modes that come to mind.

    3. You must describe with as much precision as possible the state of the system following a successful invocation of any of the features.

    4. Please do your best to write with correct spelling and grammar

      1. You may use some shorthand as appropriate, but make sure to copy edit your spec before submission

      2. Particularly egregious and lazy errors in writing may result in grade penalties for this assignment

  6. Write a program that implements a minimum of 25 tests

    1. Your test program should run all tests with a single invocation

    2. Standard output from the binary must comply with the test anything protocol (TAP)

      1. Include in the output of the testing program how the behavior differed from what was expected
    3. As a part of the minimum of 25, you must write at least 5 tests for each of the system calls read(2), write(2), and ioctl(2)

    4. Be sure to write tests that cover all of the behavior you specified, including but not limited to:

      1. Simple tests that try to isolate a specific behavior and verify it is correct

      2. More complex integration tests that verify that different system calls can work together.

      3. All failure modes that happen within the logic of the character device or as a result of user behavior

        1. That is to say, not ones resulting from extreme system conditions beyond the driver such as lack of resources
    5. Get creative when considering the incorrect usage of your API

      1. Come up with some exotic input data and insane parameters
    6. Don't forget to test for simple memory errors like usage of a null or invalid pointer

      1. Your test program should gracefully handle errors, e.g. it should not crash if a test fails or if the character driver's device file cannot be found.
  7. You will not have a driver implementation to run your test program against, however you can still verify that it is performing the right operations by pointing it at a dummy file like /dev/null or /dev/zero and verifying that it is making the right system calls with strace

    1. Be careful while writing your tests and document them well so that the person implementing the driver can understand your thinking

    2. We will not take off points for honest mistakes, but we do reserve the right to take points off if the tests are completely incoherent and prove impossible to work with

Policies & Procedures


msg = (silence)
whoami = None
singularity v0.5 https://github.com/underground-software/singularity