Imported GNU Classpath 0.90
[official-gcc.git] / libjava / classpath / native / jni / java-net / gnu_java_net_local_LocalSocketImpl.c
blob3b29001a7487eacef216f957bf1c7cfe5d26355e
1 /* gnu_java_net_local_LocalSocketImpl.c -- native local socket implementation.
2 Copyright (C) 2006 Free Software Foundation, Inc.
4 This file is a part of GNU Classpath.
6 GNU Classpath is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2 of the License, or (at
9 your option) any later version.
11 GNU Classpath is distributed in the hope that it will be useful, but
12 WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with GNU Classpath; if not, write to the Free Software
18 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301
19 USA
21 Linking this library statically or dynamically with other modules is
22 making a combined work based on this library. Thus, the terms and
23 conditions of the GNU General Public License cover the whole
24 combination.
26 As a special exception, the copyright holders of this library give you
27 permission to link this library with independent modules to produce an
28 executable, regardless of the license terms of these independent
29 modules, and to copy and distribute the resulting executable under
30 terms of your choice, provided that you also meet, for each linked
31 independent module, the terms and conditions of the license of that
32 module. An independent module is a module which is not derived from
33 or based on this library. If you modify this library, you may extend
34 this exception to your version of the library, but you are not
35 obligated to do so. If you do not wish to do so, delete this
36 exception statement from your version. */
39 #define _GNU_SOURCE
41 #ifdef HAVE_CONFIG_H
42 #include "config.h"
43 #endif /* HAVE_CONFIG_H */
45 #include <gnu_java_net_local_LocalSocketImpl.h>
47 #include <stddef.h>
48 #include "local.h"
50 #ifdef DEBUG
51 #define TRACE(msg) fprintf (stderr, "%s(%s:%d) -- %s\n", __FUNCTION__, __FILE__, __LINE__, msg)
52 #else
53 #define TRACE(msg)
54 #endif
56 static void
57 _throw (JNIEnv *env, const char *exception, const char *msg)
59 jclass _theclass = (*env)->FindClass (env, exception);
60 TRACE("begin");
61 if (!_theclass)
63 (*env)->FatalError (env, "exception class not found");
65 (*env)->ThrowNew (env, _theclass, msg);
66 TRACE("end");
69 void
70 Java_gnu_java_net_local_LocalSocketImpl_create (JNIEnv *env, jobject this, jboolean stream)
72 #ifdef ENABLE_LOCAL_SOCKETS
73 jfieldID socket_fd, created;
74 jclass clazz;
75 jint fd = (jint) local_create ((int) stream);
77 TRACE("begin");
79 if (fd < 0)
81 _throw (env, "java/io/IOException", local_error ());
82 return;
84 clazz = (*env)->GetObjectClass (env, this);
85 socket_fd = (*env)->GetFieldID (env, clazz, "socket_fd", "I");
86 if (!socket_fd)
88 return;
90 created = (*env)->GetFieldID (env, clazz, "created", "Z");
91 if (!created)
93 return;
95 (*env)->SetIntField (env, this, socket_fd, fd);
96 (*env)->SetBooleanField (env, this, created, JNI_TRUE);
98 TRACE("end");
99 #else
100 (void) this;
101 (void) stream;
102 _throw (env, "java/lang/Error", "support for local sockets not available");
103 #endif /* ENABLE_LOCAL_SOCKETS */
107 void
108 Java_gnu_java_net_local_LocalSocketImpl_listen (JNIEnv *env, jobject this, jint backlog)
110 #ifdef ENABLE_LOCAL_SOCKETS
111 jfieldID socket_fd;
112 jclass clazz;
113 int fd;
115 TRACE("begin");
117 clazz = (*env)->GetObjectClass (env, this);
118 socket_fd = (*env)->GetFieldID (env, clazz, "socket_fd", "I");
119 if (!socket_fd)
121 return;
123 fd = (int) (*env)->GetIntField (env, this, socket_fd);
124 if (local_listen (fd, (int) backlog))
126 _throw (env, "java/io/IOException", local_error ());
127 return;
130 TRACE("end");
131 #else
132 (void) this;
133 (void) backlog;
134 _throw (env, "java/lang/Error", "support for local sockets not available");
135 #endif /* ENABLE_LOCAL_SOCKETS */
139 void
140 Java_gnu_java_net_local_LocalSocketImpl_accept (JNIEnv *env, jobject this, jobject socket)
142 #ifdef ENABLE_LOCAL_SOCKETS
143 jmethodID addr_init;
144 jfieldID socket_fd, remote_addr, local_addr;
145 jclass clazz1, clazz2;
146 jobject remote, local;
147 jint fd;
148 char path[108];
150 TRACE("begin");
152 clazz1 = (*env)->GetObjectClass (env, this);
153 socket_fd = (*env)->GetFieldID (env, clazz1, "socket_fd", "I");
154 if (!socket_fd)
156 return;
158 fd = (*env)->GetIntField (env, this, socket_fd);
159 fd = (jint) local_accept ((int) fd, path);
160 if (fd < 0)
162 _throw (env, "java/io/IOException", local_error ());
163 return;
166 clazz2 = (*env)->FindClass (env, "gnu/java/net/local/LocalSocketAddress");
167 if (!clazz2)
169 return;
171 addr_init = (*env)->GetMethodID (env, clazz2, "<init>", "(Ljava/lang/String;)V");
172 if (!addr_init)
174 return;
176 remote = (*env)->NewObject (env, clazz2, addr_init, (*env)->NewStringUTF (env, path));
178 remote_addr = (*env)->GetFieldID (env, clazz1, "remote", "Lgnu/java/net/local/LocalSocketAddress;");
179 if (!remote_addr)
181 return;
183 local_addr = (*env)->GetFieldID (env, clazz1, "local", "Lgnu/java/net/local/LocalSocketAddress;");
184 if (!local_addr)
186 return;
188 local = (*env)->GetObjectField (env, this, local_addr);
189 (*env)->SetIntField (env, socket, socket_fd, fd);
190 (*env)->SetObjectField (env, socket, remote_addr, remote);
191 (*env)->SetObjectField (env, socket, local_addr, local);
193 TRACE("end");
194 #else
195 (void) this;
196 (void) socket;
197 _throw (env, "java/lang/Error", "support for local sockets not available");
198 #endif /* ENABLE_LOCAL_SOCKETS */
202 jint
203 Java_gnu_java_net_local_LocalSocketImpl_available (JNIEnv *env, jobject this)
205 #ifdef ENABLE_LOCAL_SOCKETS
206 jfieldID socket_fd;
207 jclass clazz;
208 jint avail;
210 TRACE("begin");
212 clazz = (*env)->GetObjectClass (env, this);
213 socket_fd = (*env)->GetFieldID (env, clazz, "socket_fd", "I");
214 if (!socket_fd)
216 return 0;
218 avail = (jint) local_available ((int) (*env)->GetIntField (env, this, socket_fd));
219 if (avail < 0)
221 _throw (env, "java/io/IOException", local_error ());
222 return 0;
225 TRACE("end");
227 return avail;
228 #else
229 (void) this;
230 _throw (env, "java/lang/Error", "support for local sockets not available");
231 return -1;
232 #endif /* ENABLE_LOCAL_SOCKETS */
236 void
237 Java_gnu_java_net_local_LocalSocketImpl_close (JNIEnv *env, jobject this)
239 #ifdef ENABLE_LOCAL_SOCKETS
240 jfieldID socket_fd;
241 jclass clazz;
242 int fd;
244 TRACE("begin");
246 clazz = (*env)->GetObjectClass (env, this);
247 socket_fd = (*env)->GetFieldID (env, clazz, "socket_fd", "I");
248 if (!socket_fd)
250 return;
252 fd = (int) (*env)->GetIntField (env, this, socket_fd);
253 if (local_close (fd))
255 _throw (env, "java/io/IOException", local_error ());
258 TRACE("end");
259 #else
260 (void) this;
261 _throw (env, "java/lang/Error", "support for local sockets not available");
262 #endif /* ENABLE_LOCAL_SOCKETS */
266 void
267 Java_gnu_java_net_local_LocalSocketImpl_unlink (JNIEnv *env, jobject this)
269 #ifdef ENABLE_LOCAL_SOCKETS
270 jfieldID local;
271 jmethodID get_path;
272 jclass clazz1, clazz2;
273 jobject local_ref, path;
274 char *addr_path;
276 TRACE("begin");
278 clazz1 = (*env)->GetObjectClass (env, this);
279 local = (*env)->GetFieldID (env, clazz1, "local", "Lgnu/java/net/local/LocalSocketAddress;");
280 if (!local)
282 return;
284 local_ref = (*env)->GetObjectField (env, this, local);
285 clazz2 = (*env)->GetObjectClass (env, local_ref);
286 get_path = (*env)->GetMethodID (env, clazz2, "getPath", "()Ljava/lang/String;");
287 if (!get_path)
289 return;
291 path = (*env)->CallObjectMethod (env, local_ref, get_path);
292 addr_path = (char *) (*env)->GetStringUTFChars (env, (jstring) path, NULL);
293 if (local_unlink (addr_path))
295 _throw (env, "java/io/IOException", local_error ());
297 (*env)->ReleaseStringUTFChars (env, (jstring) path, addr_path);
299 TRACE("end");
300 #else
301 (void) this;
302 _throw (env, "java/lang/Error", "support for local sockets not available");
303 #endif /* ENABLE_LOCAL_SOCKETS */
307 void
308 Java_gnu_java_net_local_LocalSocketImpl_sendUrgentData (JNIEnv *env, jobject this __attribute__((unused)), jint data __attribute__((unused)))
310 /* XXX I don't remember why I have this. Probably should just
311 remove. */
312 (*env)->FatalError (env, "Java_gnu_java_net_local_LocalSocketImpl_shutdownInput (JNIEnv *env, jobject) not implemented");
316 void
317 Java_gnu_java_net_local_LocalSocketImpl_shutdownInput (JNIEnv *env, jobject this)
319 #ifdef ENABLE_LOCAL_SOCKETS
320 jfieldID socket_fd;
321 jclass clazz;
322 int fd;
324 TRACE("begin");
326 clazz = (*env)->GetObjectClass (env, this);
327 socket_fd = (*env)->GetFieldID (env, clazz, "socket_fd", "I");
328 if (!socket_fd)
330 return;
332 fd = (*env)->GetIntField (env, this, socket_fd);
333 if (local_shutdown_input (fd))
335 _throw (env, "java/io/IOException", local_error ());
338 TRACE("end");
339 #else
340 (void) this;
341 _throw (env, "java/lang/Error", "support for local sockets not available");
342 #endif /* ENABLE_LOCAL_SOCKETS */
346 void
347 Java_gnu_java_net_local_LocalSocketImpl_shutdownOutput (JNIEnv *env, jobject this)
349 #ifdef ENABLE_LOCAL_SOCKETS
350 jfieldID socket_fd;
351 jclass clazz;
352 int fd;
354 TRACE("begin");
356 clazz = (*env)->GetObjectClass (env, this);
357 socket_fd = (*env)->GetFieldID (env, clazz, "socket_fd", "I");
358 if (!socket_fd)
360 return;
362 fd = (*env)->GetIntField (env, this, socket_fd);
363 if (local_shutdown_output (fd))
365 _throw (env, "java/io/IOException", local_error ());
368 TRACE("end");
369 #else
370 (void) this;
371 _throw (env, "java/lang/Error", "support for local sockets not available");
372 #endif /* ENABLE_LOCAL_SOCKETS */
376 void
377 Java_gnu_java_net_local_LocalSocketImpl_localBind (JNIEnv *env, jobject this, jobject address)
379 #ifdef ENABLE_LOCAL_SOCKETS
380 jfieldID socket_fd;
381 jmethodID get_path;
382 jobject path;
383 jclass clazz1, clazz2;
384 const char *addr_path;
385 int fd;
387 TRACE("begin");
389 clazz1 = (*env)->GetObjectClass (env, this);
390 socket_fd = (*env)->GetFieldID (env, clazz1, "socket_fd", "I");
391 if (!socket_fd)
393 return;
395 fd = (int) (*env)->GetIntField (env, this, socket_fd);
396 clazz2 = (*env)->GetObjectClass (env, address);
397 get_path = (*env)->GetMethodID (env, clazz2, "getPath", "()Ljava/lang/String;");
398 path = (*env)->CallObjectMethod (env, address, get_path);
399 addr_path = (*env)->GetStringUTFChars (env, (jstring) path, NULL);
400 if (local_bind (fd, addr_path))
402 _throw (env, "java/io/IOException", local_error ());
404 (*env)->ReleaseStringUTFChars (env, (jstring) path, addr_path);
406 TRACE("end");
407 #else
408 (void) this;
409 (void) address;
410 _throw (env, "java/lang/Error", "support for local sockets not available");
411 #endif /* ENABLE_LOCAL_SOCKETS */
415 void
416 Java_gnu_java_net_local_LocalSocketImpl_localConnect (JNIEnv *env, jobject this, jobject address)
418 #ifdef ENABLE_LOCAL_SOCKETS
419 jfieldID socket_fd;
420 jmethodID get_path;
421 jobject path;
422 jclass clazz1, clazz2;
423 char *addr_path;
424 int fd;
426 TRACE("begin");
428 clazz1 = (*env)->GetObjectClass (env, this);
429 socket_fd = (*env)->GetFieldID (env, clazz1, "socket_fd", "I");
430 if (!socket_fd)
432 return;
434 fd = (int) (*env)->GetIntField (env, this, socket_fd);
435 clazz2 = (*env)->GetObjectClass (env, address);
436 get_path = (*env)->GetMethodID (env, clazz2, "getPath", "()Ljava/lang/String;");
437 path = (*env)->CallObjectMethod (env, address, get_path);
438 addr_path = (char *) (*env)->GetStringUTFChars (env, (jstring) path, NULL);
439 if (local_connect (fd, addr_path))
441 _throw (env, "java/io/IOException", local_error ());
443 (*env)->ReleaseStringUTFChars (env, (jstring) path, addr_path);
445 TRACE("end");
446 #else
447 (void) this;
448 (void) address;
449 _throw (env, "java/lang/Error", "support for local sockets not available");
450 #endif /* ENABLE_LOCAL_SOCKETS */
454 jint
455 Java_gnu_java_net_local_LocalSocketImpl_read (JNIEnv *env, jobject this, jbyteArray buf, jint off, jint len)
457 #ifdef ENABLE_LOCAL_SOCKETS
458 jfieldID socket_fd;
459 jclass clazz;
460 jbyte *buffer;
461 jint count;
462 int fd;
464 TRACE("begin");
466 if (off < 0 || len < 0 || off + len > (*env)->GetArrayLength (env, buf))
468 _throw (env, "java/lang/ArrayIndexOutOfBoundsException", "");
471 clazz = (*env)->GetObjectClass (env, this);
472 socket_fd = (*env)->GetFieldID (env, clazz, "socket_fd", "I");
473 if (!socket_fd)
475 return 0;
477 fd = (int) (*env)->GetIntField (env, this, socket_fd);
478 buffer = (*env)->GetByteArrayElements (env, buf, NULL);
479 count = (jint) local_read (fd, (void *) (buffer + off), (int) len);
480 if (count < 0)
482 _throw (env, "java/io/IOException", local_error ());
484 (*env)->ReleaseByteArrayElements (env, buf, buffer, 0);
486 TRACE("end");
488 return count;
489 #else
490 (void) this;
491 (void) buf;
492 (void) off;
493 (void) len;
494 _throw (env, "java/lang/Error", "support for local sockets not available");
495 return -1;
496 #endif /* ENABLE_LOCAL_SOCKETS */
500 void
501 Java_gnu_java_net_local_LocalSocketImpl_write (JNIEnv *env, jobject this, jbyteArray buf, jint off, jint len)
503 #ifdef ENABLE_LOCAL_SOCKETS
504 jfieldID socket_fd;
505 jclass clazz;
506 jbyte *buffer;
507 int fd;
509 TRACE("begin");
511 if (off < 0 || len < 0 || off + len > (*env)->GetArrayLength (env, buf))
513 _throw (env, "java/lang/ArrayIndexOutOfBoundsException", "");
516 clazz = (*env)->GetObjectClass (env, this);
517 socket_fd = (*env)->GetFieldID (env, clazz, "socket_fd", "I");
518 if (!socket_fd)
520 return;
522 fd = (int) (*env)->GetIntField (env, this, socket_fd);
523 buffer = (*env)->GetByteArrayElements (env, buf, NULL);
524 if (local_write (fd, (void *) (buffer + off), (int) len) < 0)
526 _throw (env, "java/io/IOException", local_error ());
528 (*env)->ReleaseByteArrayElements (env, buf, buffer, JNI_ABORT);
530 TRACE("end");
531 #else
532 (void) this;
533 (void) buf;
534 (void) off;
535 (void) len;
536 _throw (env, "java/lang/Error", "support for local sockets not available");
537 #endif /* ENABLE_LOCAL_SOCKETS */