《操作系统》的实验代码。
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

77 lines
2.0 KiB

12 years ago
  1. #include <defs.h>
  2. #include <string.h>
  3. #include <iobuf.h>
  4. #include <error.h>
  5. #include <assert.h>
  6. /*
  7. * iobuf_init - init io buffer struct.
  8. * set up io_base to point to the buffer you want to transfer to, and set io_len to the length of buffer;
  9. * initialize io_offset as desired;
  10. * initialize io_resid to the total amount of data that can be transferred through this io.
  11. */
  12. struct iobuf *
  13. iobuf_init(struct iobuf *iob, void *base, size_t len, off_t offset) {
  14. iob->io_base = base;
  15. iob->io_offset = offset;
  16. iob->io_len = iob->io_resid = len;
  17. return iob;
  18. }
  19. /* iobuf_move - move data (iob->io_base ---> data OR data --> iob->io.base) in memory
  20. * @copiedp: the size of data memcopied
  21. *
  22. * iobuf_move may be called repeatedly on the same io to transfer
  23. * additional data until the available buffer space the io refers to
  24. * is exhausted.
  25. */
  26. int
  27. iobuf_move(struct iobuf *iob, void *data, size_t len, bool m2b, size_t *copiedp) {
  28. size_t alen;
  29. if ((alen = iob->io_resid) > len) {
  30. alen = len;
  31. }
  32. if (alen > 0) {
  33. void *src = iob->io_base, *dst = data;
  34. if (m2b) {
  35. void *tmp = src;
  36. src = dst, dst = tmp;
  37. }
  38. memmove(dst, src, alen);
  39. iobuf_skip(iob, alen), len -= alen;
  40. }
  41. if (copiedp != NULL) {
  42. *copiedp = alen;
  43. }
  44. return (len == 0) ? 0 : -E_NO_MEM;
  45. }
  46. /*
  47. * iobuf_move_zeros - set io buffer zero
  48. * @copiedp: the size of data memcopied
  49. */
  50. int
  51. iobuf_move_zeros(struct iobuf *iob, size_t len, size_t *copiedp) {
  52. size_t alen;
  53. if ((alen = iob->io_resid) > len) {
  54. alen = len;
  55. }
  56. if (alen > 0) {
  57. memset(iob->io_base, 0, alen);
  58. iobuf_skip(iob, alen), len -= alen;
  59. }
  60. if (copiedp != NULL) {
  61. *copiedp = alen;
  62. }
  63. return (len == 0) ? 0 : -E_NO_MEM;
  64. }
  65. /*
  66. * iobuf_skip - change the current position of io buffer
  67. */
  68. void
  69. iobuf_skip(struct iobuf *iob, size_t n) {
  70. assert(iob->io_resid >= n);
  71. iob->io_base += n, iob->io_offset += n, iob->io_resid -= n;
  72. }