|
|
1.1 root 1: /*
2:
1.1.1.3 ! root 3: Copyright 1992 Eric R. Smith.
! 4:
! 5: All rights reserved.
1.1 root 6:
7: */
8:
9:
10:
11: /* Shared memory file system */
12:
13:
14:
15: #include "mint.h"
16:
17:
18:
19:
20:
1.1.1.2 root 21: static long ARGS_ON_STACK shm_root P_((int drv, fcookie *fc));
1.1 root 22:
1.1.1.2 root 23: static long ARGS_ON_STACK shm_creat P_((fcookie *dir, const char *name, unsigned mode,
1.1 root 24:
25: int attrib, fcookie *fc));
26:
1.1.1.2 root 27: static long ARGS_ON_STACK shm_lookup P_((fcookie *dir, const char *name, fcookie *fc));
1.1 root 28:
1.1.1.2 root 29: static long ARGS_ON_STACK shm_getxattr P_((fcookie *fc, XATTR *xattr));
1.1 root 30:
1.1.1.2 root 31: static long ARGS_ON_STACK shm_chattr P_((fcookie *fc, int attrib));
1.1 root 32:
1.1.1.2 root 33: static long ARGS_ON_STACK shm_chown P_((fcookie *fc, int uid, int gid));
1.1 root 34:
1.1.1.2 root 35: static long ARGS_ON_STACK shm_chmode P_((fcookie *fc, unsigned mode));
1.1 root 36:
1.1.1.2 root 37: static long ARGS_ON_STACK shm_rmdir P_((fcookie *dir, const char *name));
1.1 root 38:
1.1.1.2 root 39: static long ARGS_ON_STACK shm_remove P_((fcookie *dir, const char *name));
1.1 root 40:
1.1.1.3 ! root 41: static long ARGS_ON_STACK shm_getname P_((fcookie *root, fcookie *dir,
! 42:
! 43: char *pathname, int size));
1.1 root 44:
1.1.1.2 root 45: static long ARGS_ON_STACK shm_rename P_((fcookie *olddir, char *oldname,
1.1 root 46:
47: fcookie *newdir, const char *newname));
48:
1.1.1.2 root 49: static long ARGS_ON_STACK shm_opendir P_((DIR *dirh, int flags));
1.1 root 50:
1.1.1.2 root 51: static long ARGS_ON_STACK shm_readdir P_((DIR *dirh, char *nm, int nmlen, fcookie *));
1.1 root 52:
1.1.1.2 root 53: static long ARGS_ON_STACK shm_rewinddir P_((DIR *dirh));
1.1 root 54:
1.1.1.2 root 55: static long ARGS_ON_STACK shm_closedir P_((DIR *dirh));
1.1 root 56:
1.1.1.2 root 57: static long ARGS_ON_STACK shm_pathconf P_((fcookie *dir, int which));
1.1 root 58:
1.1.1.2 root 59: static long ARGS_ON_STACK shm_dfree P_((fcookie *dir, long *buf));
1.1 root 60:
1.1.1.2 root 61: static DEVDRV * ARGS_ON_STACK shm_getdev P_((fcookie *fc, long *devsp));
1.1 root 62:
63:
64:
1.1.1.2 root 65: static long ARGS_ON_STACK shm_open P_((FILEPTR *f));
1.1 root 66:
1.1.1.2 root 67: static long ARGS_ON_STACK shm_write P_((FILEPTR *f, const char *buf, long bytes));
1.1 root 68:
1.1.1.2 root 69: static long ARGS_ON_STACK shm_read P_((FILEPTR *f, char *buf, long bytes));
1.1 root 70:
1.1.1.2 root 71: static long ARGS_ON_STACK shm_lseek P_((FILEPTR *f, long where, int whence));
1.1 root 72:
1.1.1.2 root 73: static long ARGS_ON_STACK shm_ioctl P_((FILEPTR *f, int mode, void *buf));
1.1 root 74:
1.1.1.2 root 75: static long ARGS_ON_STACK shm_datime P_((FILEPTR *f, short *time, int rwflag));
1.1 root 76:
1.1.1.2 root 77: static long ARGS_ON_STACK shm_close P_((FILEPTR *f, int pid));
1.1 root 78:
79:
80:
81: /* dummy routines from biosfs.c */
82:
1.1.1.2 root 83: extern long ARGS_ON_STACK null_select P_((FILEPTR *f, long p, int mode));
1.1 root 84:
1.1.1.2 root 85: extern void ARGS_ON_STACK null_unselect P_((FILEPTR *f, long p, int mode));
1.1 root 86:
87:
88:
89: static short shmtime, shmdate;
90:
91:
92:
93: #define SHMNAME_MAX 15
94:
95:
96:
97: typedef struct shmfile {
98:
99: struct shmfile *next;
100:
101: char filename[SHMNAME_MAX+1];
102:
103: int uid, gid;
104:
105: short time, date;
106:
107: unsigned mode;
108:
109: int inuse;
110:
111: MEMREGION *reg;
112:
113: } SHMFILE;
114:
115:
116:
117: SHMFILE *shmroot = 0;
118:
119:
120:
121: DEVDRV shm_device = {
122:
123: shm_open, shm_write, shm_read, shm_lseek, shm_ioctl, shm_datime,
124:
125: shm_close, null_select, null_unselect
126:
127: };
128:
129:
130:
131: FILESYS shm_filesys = {
132:
133: (FILESYS *)0,
134:
1.1.1.3 ! root 135: FS_LONGPATH,
1.1 root 136:
137: shm_root,
138:
139: shm_lookup, shm_creat, shm_getdev, shm_getxattr,
140:
141: shm_chattr, shm_chown, shm_chmode,
142:
143: nomkdir, shm_rmdir, shm_remove, shm_getname, shm_rename,
144:
145: shm_opendir, shm_readdir, shm_rewinddir, shm_closedir,
146:
147: shm_pathconf, shm_dfree,
148:
149: nowritelabel, noreadlabel, nosymlink, noreadlink, nohardlink,
150:
151: nofscntl, nodskchng
152:
153: };
154:
155:
156:
1.1.1.2 root 157: long ARGS_ON_STACK
1.1 root 158:
159: shm_root(drv, fc)
160:
161: int drv;
162:
163: fcookie *fc;
164:
165: {
166:
1.1.1.2 root 167: if ((unsigned)drv == SHMDRV) {
1.1 root 168:
169: fc->fs = &shm_filesys;
170:
171: fc->dev = drv;
172:
173: fc->index = 0L;
174:
175: return 0;
176:
177: }
178:
179: fc->fs = 0;
180:
181: return EINTRN;
182:
183: }
184:
185:
186:
1.1.1.2 root 187: static long ARGS_ON_STACK
1.1 root 188:
189: shm_lookup(dir, name, fc)
190:
191: fcookie *dir;
192:
193: const char *name;
194:
195: fcookie *fc;
196:
197: {
198:
199: SHMFILE *s;
200:
201:
202:
203: if (dir->index != 0) {
204:
1.1.1.2 root 205: DEBUG(("shm_lookup: bad directory"));
1.1 root 206:
207: return EPTHNF;
208:
209: }
210:
211:
212:
213: /* special case: an empty name in a directory means that directory */
214:
215: /* so does "." */
216:
217: if (!*name || (name[0] == '.' && name[1] == 0)) {
218:
219: *fc = *dir;
220:
221: return 0;
222:
223: }
224:
225:
226:
227: /* another special case: ".." could be a mount point */
228:
229: if (!strcmp(name, "..")) {
230:
231: *fc = *dir;
232:
233: return EMOUNT;
234:
235: }
236:
237:
238:
239: for (s = shmroot; s; s = s->next) {
240:
241: if (!stricmp(s->filename,name))
242:
243: break;
244:
245: }
246:
247:
248:
249: if (!s) {
250:
1.1.1.2 root 251: DEBUG(("shm_lookup: name not found"));
1.1 root 252:
253: return EFILNF;
254:
255: } else {
256:
257: fc->index = (long)s;
258:
259: fc->fs = &shm_filesys;
260:
1.1.1.2 root 261: fc->dev = SHMDRV;
1.1 root 262:
263: }
264:
265: return 0;
266:
267: }
268:
269:
270:
1.1.1.2 root 271: static long ARGS_ON_STACK
1.1 root 272:
273: shm_getxattr(fc, xattr)
274:
275: fcookie *fc;
276:
277: XATTR *xattr;
278:
279: {
280:
281: SHMFILE *s;
282:
283:
284:
285: xattr->blksize = 1;
286:
287: if (fc->index == 0) {
288:
289: /* the root directory */
290:
291: xattr->index = 0;
292:
1.1.1.2 root 293: xattr->dev = SHMDRV;
1.1 root 294:
295: xattr->nlink = 1;
296:
297: xattr->uid = xattr->gid = 0;
298:
299: xattr->size = xattr->nblocks = 0;
300:
301: xattr->mtime = xattr->atime = xattr->ctime = shmtime;
302:
303: xattr->mdate = xattr->adate = xattr->cdate = shmdate;
304:
305: xattr->mode = S_IFDIR | DEFAULT_DIRMODE;
306:
307: xattr->attr = FA_DIR;
308:
309: return 0;
310:
311: }
312:
313:
314:
315: s = (SHMFILE *)fc->index;
316:
317: xattr->index = (long) s;
318:
1.1.1.2 root 319: xattr->dev = SHMDRV;
1.1 root 320:
321: xattr->uid = s->uid; xattr->gid = s->gid;
322:
1.1.1.2 root 323: if (s->reg) {
1.1 root 324:
325: xattr->size = xattr->nblocks = s->reg->len;
326:
1.1.1.2 root 327: xattr->nlink = s->reg->links + 1;
328:
329: } else {
1.1 root 330:
331: xattr->size = xattr->nblocks = 0;
332:
1.1.1.2 root 333: xattr->nlink = 1;
1.1 root 334:
1.1.1.2 root 335: }
1.1 root 336:
337: xattr->mtime = xattr->ctime = xattr->atime = s->time;
338:
339: xattr->mdate = xattr->cdate = xattr->adate = s->date;
340:
1.1.1.2 root 341: xattr->mode = s->mode;
1.1 root 342:
1.1.1.2 root 343: xattr->attr = (s->mode & (S_IWUSR|S_IWGRP|S_IWOTH)) ? 0 :
344:
345: FA_RDONLY;
1.1 root 346:
347: return 0;
348:
349: }
350:
351:
352:
1.1.1.2 root 353: static long ARGS_ON_STACK
1.1 root 354:
355: shm_chattr(fc, attrib)
356:
357: fcookie *fc;
358:
359: int attrib;
360:
361: {
362:
1.1.1.2 root 363: SHMFILE *s;
364:
365:
366:
367: s = (SHMFILE *)fc->index;
368:
369: if (!s) return EACCDN;
370:
371:
372:
373: if (attrib & FA_RDONLY) {
374:
375: s->mode &= ~(S_IWUSR|S_IWGRP|S_IWOTH);
376:
377: } else if ( !(s->mode & (S_IWUSR|S_IWGRP|S_IWOTH)) ) {
378:
379: s->mode |= (S_IWUSR|S_IWGRP|S_IWOTH);
380:
381: }
382:
1.1 root 383: return 0;
384:
385: }
386:
387:
388:
1.1.1.2 root 389: static long ARGS_ON_STACK
1.1 root 390:
391: shm_chown(fc, uid, gid)
392:
393: fcookie *fc;
394:
395: int uid, gid;
396:
397: {
398:
399: SHMFILE *s;
400:
401:
402:
403: s = (SHMFILE *)fc->index;
404:
405: if (!s)
406:
1.1.1.2 root 407: return EACCDN;
1.1 root 408:
409: s->uid = uid;
410:
411: s->gid = gid;
412:
413: return 0;
414:
415: }
416:
417:
418:
1.1.1.2 root 419: static long ARGS_ON_STACK
1.1 root 420:
421: shm_chmode(fc, mode)
422:
423: fcookie *fc;
424:
425: unsigned mode;
426:
427: {
428:
429: SHMFILE *s;
430:
431:
432:
433: s = (SHMFILE *)fc->index;
434:
435: if (!s)
436:
437: return EINVFN;
438:
439: s->mode = mode;
440:
441: return 0;
442:
443: }
444:
445:
446:
1.1.1.2 root 447: static long ARGS_ON_STACK
1.1 root 448:
449: shm_rmdir(dir, name)
450:
451: fcookie *dir;
452:
453: const char *name;
454:
455: {
456:
1.1.1.2 root 457: UNUSED(dir); UNUSED(name);
458:
459:
460:
1.1 root 461: return EPTHNF;
462:
463: }
464:
465:
466:
1.1.1.2 root 467: static long ARGS_ON_STACK
1.1 root 468:
469: shm_remove(dir, name)
470:
471: fcookie *dir;
472:
473: const char *name;
474:
475: {
476:
477: SHMFILE *s, **old;
478:
479:
480:
481: if (dir->index != 0)
482:
483: return EPTHNF;
484:
485:
486:
487: old = &shmroot;
488:
489: for (s = shmroot; s; s = s->next) {
490:
491: if (!stricmp(s->filename, name))
492:
493: break;
494:
495: old = &s->next;
496:
497: }
498:
499: if (!s)
500:
501: return EFILNF;
502:
503: if (s->inuse)
504:
505: return EACCDN;
506:
507: *old = s->next;
508:
509:
510:
511: s->reg->links--;
512:
513: if (s->reg->links <= 0) {
514:
515: free_region(s->reg);
516:
517: }
518:
519: kfree(s);
520:
521: shmtime = timestamp;
522:
523: shmdate = datestamp;
524:
525: return 0;
526:
527: }
528:
529:
530:
1.1.1.2 root 531: static long ARGS_ON_STACK
1.1 root 532:
1.1.1.3 ! root 533: shm_getname(root, dir, pathname, size)
1.1 root 534:
535: fcookie *root, *dir; char *pathname;
536:
1.1.1.3 ! root 537: int size;
! 538:
1.1 root 539: {
540:
1.1.1.2 root 541: UNUSED(root); UNUSED(dir);
542:
543:
544:
1.1.1.3 ! root 545: /* BUG: 'size' should be used in a more meaningful way */
! 546:
! 547: if (size <= 0) return ERANGE;
! 548:
1.1 root 549: *pathname = 0;
550:
551: return 0;
552:
553: }
554:
555:
556:
1.1.1.2 root 557: static long ARGS_ON_STACK
1.1 root 558:
559: shm_rename(olddir, oldname, newdir, newname)
560:
561: fcookie *olddir;
562:
563: char *oldname;
564:
565: fcookie *newdir;
566:
567: const char *newname;
568:
569: {
570:
571: SHMFILE *s;
572:
573:
574:
575: if (olddir->index != 0 || newdir->index != 0)
576:
577: return EPTHNF;
578:
579:
580:
581: /* verify that "newname" doesn't exist */
582:
583: for (s = shmroot; s; s = s->next)
584:
585: if (!stricmp(s->filename, newname))
586:
587: return EACCDN;
588:
589:
590:
591: for (s = shmroot; s; s = s->next)
592:
593: if (!stricmp(s->filename, oldname))
594:
595: break;
596:
597: if (!s)
598:
599: return EFILNF;
600:
601:
602:
603: strncpy(s->filename, newname, SHMNAME_MAX);
604:
605: shmtime = timestamp;
606:
607: shmdate = datestamp;
608:
609: return 0;
610:
611: }
612:
613:
614:
1.1.1.2 root 615: static long ARGS_ON_STACK
1.1 root 616:
617: shm_opendir(dirh, flags)
618:
619: DIR *dirh;
620:
621: int flags;
622:
623: {
624:
1.1.1.2 root 625: UNUSED(flags);
626:
627:
628:
1.1 root 629: dirh->index = 0;
630:
631: return 0;
632:
633: }
634:
635:
636:
1.1.1.2 root 637: static long ARGS_ON_STACK
1.1 root 638:
639: shm_readdir(dirh, name, namelen, fc)
640:
641: DIR *dirh;
642:
643: char *name;
644:
645: int namelen;
646:
647: fcookie *fc;
648:
649: {
650:
651: int i;
652:
653: int giveindex = (dirh->flags == 0);
654:
655: SHMFILE *s;
656:
657:
658:
659: s = shmroot;
660:
661: i = dirh->index++;
662:
663: while (i > 0 && s != 0) {
664:
665: s = s->next;
666:
667: --i;
668:
669: }
670:
671: if (!s)
672:
673: return ENMFIL;
674:
675:
676:
677: fc->index = (long)s;
678:
679: fc->fs = &shm_filesys;
680:
1.1.1.2 root 681: fc->dev = SHMDRV;
1.1 root 682:
683:
684:
685: if (giveindex) {
686:
1.1.1.2 root 687: namelen -= (int)sizeof(long);
1.1 root 688:
689: if (namelen <= 0) return ERANGE;
690:
691: *((long *)name) = (long)s;
692:
693: name += sizeof(long);
694:
695: }
696:
697: if (namelen < strlen(s->filename))
698:
699: return ENAMETOOLONG;
700:
701: strcpy(name, s->filename);
702:
703: return 0;
704:
705: }
706:
707:
708:
1.1.1.2 root 709: static long ARGS_ON_STACK
1.1 root 710:
711: shm_rewinddir(dirh)
712:
713: DIR *dirh;
714:
715: {
716:
717: dirh->index = 0;
718:
719: return 0;
720:
721: }
722:
723:
724:
1.1.1.2 root 725: static long ARGS_ON_STACK
1.1 root 726:
727: shm_closedir(dirh)
728:
729: DIR *dirh;
730:
731: {
732:
1.1.1.2 root 733: UNUSED(dirh);
734:
1.1 root 735: return 0;
736:
737: }
738:
739:
740:
1.1.1.2 root 741: static long ARGS_ON_STACK
1.1 root 742:
743: shm_pathconf(dir, which)
744:
745: fcookie *dir;
746:
747: int which;
748:
749: {
750:
1.1.1.2 root 751: UNUSED(dir);
752:
753:
754:
1.1 root 755: switch(which) {
756:
757: case -1:
758:
759: return DP_MAXREQ;
760:
761: case DP_IOPEN:
762:
763: return UNLIMITED; /* no internal limit on open files */
764:
765: case DP_MAXLINKS:
766:
767: return 1; /* we don't have hard links */
768:
769: case DP_PATHMAX:
770:
771: return PATH_MAX; /* max. path length */
772:
773: case DP_NAMEMAX:
774:
775: return SHMNAME_MAX; /* max. length of individual name */
776:
777: case DP_ATOMIC:
778:
779: return UNLIMITED; /* all writes are atomic */
780:
781: case DP_TRUNC:
782:
783: return DP_AUTOTRUNC; /* file names are truncated */
784:
785: case DP_CASE:
786:
787: return DP_CASEINSENS; /* case preserved, but ignored */
788:
789: default:
790:
791: return EINVFN;
792:
793: }
794:
795: }
796:
797:
798:
1.1.1.2 root 799: static long ARGS_ON_STACK
1.1 root 800:
801: shm_dfree(dir, buf)
802:
803: fcookie *dir;
804:
805: long *buf;
806:
807: {
808:
809: long size;
810:
811: /* "sector" size is the size of the smallest amount of memory that can be
812:
813: allocated. see mem.h for the definition of ROUND
814:
815: */
816:
817: long secsiz = ROUND(1);
818:
819:
820:
1.1.1.2 root 821: UNUSED(dir);
822:
823:
824:
1.1 root 825: size = tot_rsize(core, 0) + tot_rsize(alt, 0);
826:
827: *buf++ = size/secsiz; /* number of free clusters */
828:
829: size = tot_rsize(core, 1) + tot_rsize(alt, 1);
830:
831: *buf++ = size/secsiz; /* total number of clusters */
832:
833: *buf++ = secsiz; /* sector size (bytes) */
834:
1.1.1.2 root 835: *buf = 1; /* cluster size (in sectors) */
1.1 root 836:
837: return 0;
838:
839: }
840:
841:
842:
1.1.1.2 root 843: static DEVDRV * ARGS_ON_STACK
1.1 root 844:
845: shm_getdev(fc, devsp)
846:
847: fcookie *fc;
848:
849: long *devsp;
850:
851: {
852:
853: SHMFILE *s;
854:
855:
856:
857: s = (SHMFILE *)fc->index;
858:
859:
860:
861: *devsp = (long)s;
862:
863: return &shm_device;
864:
865: }
866:
867:
868:
869: /*
870:
871: * create a shared memory region
872:
873: */
874:
875:
876:
1.1.1.2 root 877: static long ARGS_ON_STACK
1.1 root 878:
879: shm_creat(dir, name, mode, attrib, fc)
880:
881: fcookie *dir;
882:
883: const char *name;
884:
885: unsigned mode;
886:
887: int attrib;
888:
889: fcookie *fc;
890:
891: {
892:
893: SHMFILE *s;
894:
895:
896:
1.1.1.2 root 897: UNUSED(attrib);
898:
1.1 root 899: /*
900:
901: * see if the name already exists
902:
903: */
904:
905: for (s = shmroot; s; s = s->next) {
906:
907: if (!stricmp(s->filename, name)) {
908:
1.1.1.2 root 909: DEBUG(("shm_creat: file exists"));
1.1 root 910:
911: return EACCDN;
912:
913: }
914:
915: }
916:
917:
918:
919: s = (SHMFILE *)kmalloc(SIZEOF(SHMFILE));
920:
921: if (!s)
922:
923: return ENSMEM;
924:
925:
926:
927: s->inuse = 0;
928:
929: strncpy(s->filename, name, SHMNAME_MAX);
930:
931: s->filename[SHMNAME_MAX] = 0;
932:
933: s->uid = curproc->ruid;
934:
935: s->gid = curproc->rgid;
936:
937: s->mode = mode;
938:
939: s->next = shmroot;
940:
941: s->reg = 0;
942:
943: s->time = shmtime = timestamp;
944:
945: s->date = shmdate = datestamp;
946:
947: shmroot = s;
948:
949:
950:
951: fc->fs = &shm_filesys;
952:
953: fc->index = (long)s;
954:
955: fc->dev = dir->dev;
956:
957:
958:
959: return 0;
960:
961: }
962:
963:
964:
965: /*
966:
967: * Shared memory device driver
968:
969: */
970:
971:
972:
973: /*
974:
975: * BUG: file locking and the O_SHMODE restrictions are not implemented
976:
977: * for shared memory
978:
979: */
980:
981:
982:
1.1.1.2 root 983: static long ARGS_ON_STACK
1.1 root 984:
985: shm_open(f)
986:
987: FILEPTR *f;
988:
989: {
990:
991: SHMFILE *s;
992:
993:
994:
995: s = (SHMFILE *)f->devinfo;
996:
997: s->inuse++;
998:
999: return 0;
1000:
1001: }
1002:
1003:
1004:
1.1.1.2 root 1005: static long ARGS_ON_STACK
1.1 root 1006:
1007: shm_write(f, buf, nbytes)
1008:
1009: FILEPTR *f; const char *buf; long nbytes;
1010:
1011: {
1012:
1013: SHMFILE *s;
1014:
1015: char *where;
1016:
1017: long bytes_written = 0;
1018:
1019:
1020:
1021: s = (SHMFILE *)f->devinfo;
1022:
1023: if (!s->reg)
1024:
1025: return 0;
1026:
1027:
1028:
1029: if (nbytes + f->pos > s->reg->len)
1030:
1031: nbytes = s->reg->len - f->pos;
1032:
1033:
1034:
1035: where = (char *)s->reg->loc + f->pos;
1036:
1037:
1038:
1039: /* BUG: memory read/writes should check for valid addresses */
1040:
1041:
1042:
1.1.1.2 root 1043: TRACE(("shm_write: %ld bytes to %lx", nbytes, where));
1.1 root 1044:
1045:
1046:
1047: while (nbytes-- > 0) {
1048:
1049: *where++ = *buf++;
1050:
1051: bytes_written++;
1052:
1053: }
1054:
1055: f->pos += bytes_written;
1056:
1057: s->time = timestamp;
1058:
1059: s->date = datestamp;
1060:
1061: return bytes_written;
1062:
1063: }
1064:
1065:
1066:
1.1.1.2 root 1067: static long ARGS_ON_STACK
1.1 root 1068:
1069: shm_read(f, buf, nbytes)
1070:
1071: FILEPTR *f; char *buf; long nbytes;
1072:
1073: {
1074:
1075: SHMFILE *s;
1076:
1077: char *where;
1078:
1079: long bytes_read = 0;
1080:
1081:
1082:
1083: s = (SHMFILE *)f->devinfo;
1084:
1085: if (!(s->reg))
1086:
1087: return 0;
1088:
1089:
1090:
1091: if (nbytes + f->pos > s->reg->len)
1092:
1093: nbytes = s->reg->len - f->pos;
1094:
1095:
1096:
1097: where = (char *)s->reg->loc + f->pos;
1098:
1099:
1100:
1.1.1.2 root 1101: TRACE(("shm_read: %ld bytes from %lx", nbytes, where));
1.1 root 1102:
1103:
1104:
1105: while (nbytes-- > 0) {
1106:
1107: *buf++ = *where++;
1108:
1109: bytes_read++;
1110:
1111: }
1112:
1113: f->pos += bytes_read;
1114:
1115: return bytes_read;
1116:
1117: }
1118:
1119:
1120:
1121: /*
1122:
1123: * shm_ioctl: currently, the only IOCTL's available are:
1124:
1125: * SHMSETBLK: set the address of the shared memory file. This
1126:
1127: * call may only be made once per region, and then only
1128:
1129: * if the region is open for writing.
1130:
1131: * SHMGETBLK: get the address of the shared memory region. This
1132:
1133: * call fails (returns 0) if SHMSETBLK has not been
1134:
1135: * called yet for this shared memory file.
1136:
1137: */
1138:
1139:
1140:
1.1.1.2 root 1141: static long ARGS_ON_STACK
1.1 root 1142:
1143: shm_ioctl(f, mode, buf)
1144:
1145: FILEPTR *f; int mode; void *buf;
1146:
1147: {
1148:
1149: SHMFILE *s;
1150:
1151: MEMREGION *m;
1152:
1153: int i;
1154:
1155: long r;
1156:
1157:
1158:
1159: s = (SHMFILE *)f->devinfo;
1160:
1161: switch(mode) {
1162:
1163: case SHMSETBLK:
1164:
1165: if (s->reg) {
1166:
1.1.1.2 root 1167: DEBUG(("Fcntl: SHMSETBLK already performed for %s",
1.1 root 1168:
1.1.1.2 root 1169: s->filename));
1.1 root 1170:
1171: return ERANGE;
1172:
1173: }
1174:
1175: if ((f->flags & O_RWMODE) == O_RDONLY) {
1176:
1.1.1.2 root 1177: DEBUG(("Fcntl: SHMSETBLK: %s was opened read-only",
1.1 root 1178:
1.1.1.2 root 1179: s->filename));
1.1 root 1180:
1181: return EACCDN;
1182:
1183: }
1184:
1185: /* find the memory region to be attached */
1186:
1187: m = 0;
1188:
1189: for (i = curproc->num_reg - 1; i >= 0; i--) {
1190:
1191: if (curproc->addr[i] == (virtaddr)buf) {
1192:
1193: m = curproc->mem[i];
1194:
1195: break;
1196:
1197: }
1198:
1199: }
1200:
1201: if (!m || !buf) {
1202:
1.1.1.2 root 1203: DEBUG(("Fcntl: SHMSETBLK: bad address %lx", buf));
1.1 root 1204:
1205: return EIMBA;
1206:
1207: }
1208:
1209: m->links++;
1210:
1211: s->reg = m;
1212:
1213: return 0;
1214:
1215: case SHMGETBLK:
1216:
1.1.1.2 root 1217: if ((m = s->reg) == 0) {
1.1 root 1218:
1.1.1.2 root 1219: DEBUG(("Fcntl: no address for SHMGETBLK"));
1.1 root 1220:
1221: return 0;
1222:
1223: }
1224:
1225: /* check for memory limits */
1226:
1227: if (curproc->maxmem) {
1228:
1229: if (m->len > curproc->maxmem - memused(curproc)) {
1230:
1.1.1.2 root 1231: DEBUG(("Fcntl: SHMGETBLK would violate memory limits"));
1.1 root 1232:
1233: return 0;
1234:
1235: }
1236:
1237: }
1238:
1239: return (long)attach_region(curproc, m);
1240:
1241: case FIONREAD:
1242:
1243: case FIONWRITE:
1244:
1245: if (s->reg == 0) {
1246:
1247: r = 0;
1248:
1249: } else {
1250:
1251: r = s->reg->len - f->pos;
1252:
1253: if (r < 0) r = 0;
1254:
1255: }
1256:
1257: *((long *)buf) = r;
1258:
1259: return 0;
1260:
1261: default:
1262:
1.1.1.2 root 1263: DEBUG(("shmfs: bad Fcntl command"));
1.1 root 1264:
1265: }
1266:
1267: return EINVFN;
1268:
1269: }
1270:
1271:
1272:
1.1.1.2 root 1273: static long ARGS_ON_STACK
1.1 root 1274:
1275: shm_lseek(f, where, whence)
1276:
1277: FILEPTR *f; long where; int whence;
1278:
1279: {
1280:
1.1.1.2 root 1281: long newpos, maxpos;
1.1 root 1282:
1283: SHMFILE *s;
1284:
1285:
1286:
1287: s = (SHMFILE *)f->devinfo;
1288:
1289:
1290:
1291: if (s->reg)
1292:
1293: maxpos = s->reg->len;
1294:
1295: else
1296:
1297: maxpos = 0;
1298:
1299:
1300:
1301: switch(whence) {
1302:
1303: case 0:
1304:
1305: newpos = where;
1306:
1307: break;
1308:
1309: case 1:
1310:
1311: newpos = f->pos + where;
1312:
1313: break;
1314:
1315: case 2:
1316:
1317: newpos = maxpos - where;
1318:
1319: break;
1320:
1321: default:
1322:
1323: return EINVFN;
1324:
1325: }
1326:
1327:
1328:
1329: if (newpos < 0 || newpos > maxpos)
1330:
1331: return ERANGE;
1332:
1333:
1334:
1335: f->pos = newpos;
1336:
1337: return newpos;
1338:
1339: }
1340:
1341:
1342:
1.1.1.2 root 1343: static long ARGS_ON_STACK
1.1 root 1344:
1345: shm_datime(f, timeptr, rwflag)
1346:
1347: FILEPTR *f;
1348:
1349: short *timeptr;
1350:
1351: int rwflag;
1352:
1353: {
1354:
1355: SHMFILE *s;
1356:
1357:
1358:
1359: s = (SHMFILE *)f->devinfo;
1360:
1361: if (rwflag) {
1362:
1363: s->time = *timeptr++;
1364:
1365: s->date = *timeptr;
1366:
1367: } else {
1368:
1369: *timeptr++ = s->time;
1370:
1.1.1.2 root 1371: *timeptr = s->date;
1.1 root 1372:
1373: }
1374:
1375: return 0;
1376:
1377: }
1378:
1379:
1380:
1.1.1.2 root 1381: static long ARGS_ON_STACK
1.1 root 1382:
1383: shm_close(f, pid)
1384:
1385: FILEPTR *f;
1386:
1387: int pid;
1388:
1389: {
1390:
1391: SHMFILE *s;
1392:
1393:
1394:
1.1.1.2 root 1395: UNUSED(pid);
1396:
1.1 root 1397: if (f->links <= 0) {
1398:
1399: s = (SHMFILE *)f->devinfo;
1400:
1401: s->inuse--;
1402:
1403: }
1404:
1405: return 0;
1406:
1407: }
1408:
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.