PS2SDK
PS2 Homebrew Libraries
Loading...
Searching...
No Matches
fdman.c
Go to the documentation of this file.
1/*
2# _____ ___ ____ ___ ____
3# ____| | ____| | | |____|
4# | ___| |____ ___| ____| | \ PS2DEV Open Source Project.
5#-----------------------------------------------------------------------
6# (C)2001, Gustavo Scotti (gustavo@scotti.com)
7# (c) 2003 Marcus R. Brown <mrbrown@0xd6.org>
8# (c) 2023 Francisco Javier Trujillo Mata <fjtrujy@gmail.com>
9# Licenced under Academic Free License version 2.0
10# Review ps2sdk README & LICENSE files for further details.
11*/
12
18#include <string.h>
19#include <stdlib.h>
20#include <errno.h>
21#include <unistd.h>
22
23#include <kernel.h>
24#include "fdman.h"
25
26#ifdef F___fdman_sema
27int __fdman_sema = -1;
28#else
29extern int __fdman_sema;
30#endif
31
32#ifdef F___descriptor_data_pool
33__descriptormap_type __descriptor_data_pool[__FILENO_MAX];
34#else
35extern __descriptormap_type __descriptor_data_pool[__FILENO_MAX];
36#endif
37
38#ifdef F___descriptormap
39__descriptormap_type *__descriptormap[__FILENO_MAX];
40#else
41extern __descriptormap_type *__descriptormap[__FILENO_MAX];
42#endif
43
44
45#ifdef F___fdman_init
46void __fdman_init()
47{
48 ee_sema_t sema;
49
50 /* Initialize mutex */
51 sema.init_count = 1;
52 sema.max_count = 1;
53 sema.option = 0;
54 __fdman_sema = CreateSema(&sema);
55 if (__fdman_sema < 0) {
56 abort();
57 }
58
59 /* Initialize descriptor data*/
60 memset(__descriptor_data_pool, 0, sizeof(__descriptormap_type) *__FILENO_MAX);
61 /* Initialize descriptor map*/
62 memset(__descriptormap, 0, sizeof(__descriptormap_type*)*__FILENO_MAX);
63
64 // We assume STDIN_FILENO, STDOUT_FILENO, STDERR_FILENO are initialized
65 __descriptormap[STDIN_FILENO] = &__descriptor_data_pool[STDIN_FILENO];
66 __libcglue_init_stdio(&(__descriptormap[STDIN_FILENO]->info), 0);
67
68 __descriptormap[STDOUT_FILENO] = &__descriptor_data_pool[STDOUT_FILENO];
69 __libcglue_init_stdio(&(__descriptormap[STDOUT_FILENO]->info), 1);
70
71 __descriptormap[STDERR_FILENO] = &__descriptor_data_pool[STDERR_FILENO];
72 __libcglue_init_stdio(&(__descriptormap[STDERR_FILENO]->info), 1 /* ioman doesn't have 2 (stderr) by default, so just use 1 (stdout) */);
73}
74#endif
75
76#ifdef F___fdman_deinit
77void __fdman_deinit()
78{
79 if (__fdman_sema > 0) {
80 DeleteSema(__fdman_sema);
81 }
82}
83#endif
84
85
86#ifdef F___fdman_get_new_descriptor
87int __fdman_get_new_descriptor()
88{
89 int i = 0;
90
91 WaitSema(__fdman_sema); /* lock here to make thread safe */
92 for (i = 0; i < __FILENO_MAX; i++) {
93 if (__descriptormap[i] == NULL) {
94 __descriptormap[i] = &__descriptor_data_pool[i];
95 __descriptormap[i]->ref_count++;
96 SignalSema(__fdman_sema); /* release lock */
97 return i;
98 }
99 }
100 SignalSema(__fdman_sema); /* release lock */
101
102 errno = ENOMEM;
103 return -1;
104}
105#endif
106
107
108#ifdef F___fdman_get_dup_descriptor
109int __fdman_get_dup_descriptor(int fd)
110{
111 int i = 0;
112
113 if (!__IS_FD_VALID(fd)) {
114 errno = EBADF;
115 return -1;
116 }
117
118 WaitSema(__fdman_sema); /* lock here to make thread safe */
119 for (i = 0; i < __FILENO_MAX; i++) {
120 if (__descriptormap[i] == NULL) {
121 __descriptormap[i] = &__descriptor_data_pool[fd];
122 __descriptormap[i]->ref_count++;
123 SignalSema(__fdman_sema); /* release lock */
124 return i;
125 }
126 }
127 SignalSema(__fdman_sema); /* release lock */
128
129 errno = ENOMEM;
130 return -1;
131}
132#endif
133
134#ifdef F___fdman_get_dup_descriptor
135int __fdman_get_dup2_descriptor(int fd, int newfd)
136{
137 if (!__IS_FD_VALID(fd)) {
138 errno = EBADF;
139 return -1;
140 }
141
142 WaitSema(__fdman_sema); /* lock here to make thread safe */
143 __descriptormap[newfd] = &__descriptor_data_pool[fd];
144 __descriptormap[newfd]->ref_count++;
145 SignalSema(__fdman_sema); /* release lock */
146
147 return newfd;
148}
149#endif
150
151#ifdef F___fdman_release_descriptor
152void __fdman_release_descriptor(int fd)
153{
154 if (!__IS_FD_VALID(fd)) {
155 errno = EBADF;
156 return;
157 }
158
159 __descriptormap[fd]->ref_count--;
160
161 if (__descriptormap[fd]->ref_count == 0) {
162 memset(__descriptormap[fd], 0, sizeof(__descriptormap_type));
163 }
164 __descriptormap[fd] = NULL;
165}
166#endif
#define ENOMEM
Definition errno.h:43
#define EBADF
Definition errno.h:37