OSDN Git Service

2258f2f3d016909e441ed64068abaa7b2afbb323
[pf3gnuchains/gcc-fork.git] / libgfortran / caf / single.c
1 /* Single-image implementation of GNU Fortran Coarray Library
2    Copyright (C) 2011
3    Free Software Foundation, Inc.
4    Contributed by Tobias Burnus <burnus@net-b.de>
5
6 This file is part of the GNU Fortran Coarray Runtime Library (libcaf).
7
8 Libcaf is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 3, or (at your option)
11 any later version.
12
13 Libcaf is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16 GNU General Public License for more details.
17
18 Under Section 7 of GPL version 3, you are granted additional
19 permissions described in the GCC Runtime Library Exception, version
20 3.1, as published by the Free Software Foundation.
21
22 You should have received a copy of the GNU General Public License and
23 a copy of the GCC Runtime Library Exception along with this program;
24 see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see
25 <http://www.gnu.org/licenses/>.  */
26
27 #include "libcaf.h"
28 #include <stdio.h>  /* For fputs and fprintf.  */
29 #include <stdlib.h> /* For exit and malloc.  */
30 #include <string.h> /* For memcpy and memset.  */
31 #include <stdarg.h> /* For variadic arguments.  */
32
33 /* Define GFC_CAF_CHECK to enable run-time checking.  */
34 /* #define GFC_CAF_CHECK  1  */
35
36 /* Single-image implementation of the CAF library.
37    Note: For performance reasons -fcoarry=single should be used
38    rather than this library.  */
39
40 /* Global variables.  */
41 caf_static_t *caf_static_list = NULL;
42
43
44 /* Keep in sync with mpi.c.  */
45 static void
46 caf_runtime_error (const char *message, ...)
47 {
48   va_list ap;
49   fprintf (stderr, "Fortran runtime error: ");
50   va_start (ap, message);
51   fprintf (stderr, message, ap);
52   va_end (ap);
53   fprintf (stderr, "\n");
54
55   /* FIXME: Shutdown the Fortran RTL to flush the buffer.  PR 43849.  */
56   exit (EXIT_FAILURE);
57 }
58
59 void
60 _gfortran_caf_init (int *argc __attribute__ ((unused)),
61                     char ***argv __attribute__ ((unused)),
62                     int *this_image, int *num_images)
63 {
64   *this_image = 1;
65   *num_images = 1;
66 }
67
68
69 void
70 _gfortran_caf_finalize (void)
71 {
72   while (caf_static_list != NULL)
73     {
74       free(caf_static_list->token[0]);
75       caf_static_list = caf_static_list->prev;
76     }
77 }
78
79
80 void *
81 _gfortran_caf_register (ptrdiff_t size, caf_register_t type, void **token,
82                         int *stat, char *errmsg, int errmsg_len)
83 {
84   void *local;
85
86   local = malloc (size);
87   token = malloc (sizeof (void*) * 1);
88   token[0] = local;
89
90   if (unlikely (local == NULL || token == NULL))
91     {
92       const char msg[] = "Failed to allocate coarray";
93       if (stat)
94         {
95           *stat = 1;
96           if (errmsg_len > 0)
97             {
98               int len = ((int) sizeof (msg) > errmsg_len) ? errmsg_len
99                                                           : (int) sizeof (msg);
100               memcpy (errmsg, msg, len);
101               if (errmsg_len > len)
102                 memset (&errmsg[len], ' ', errmsg_len-len);
103             }
104           return NULL;
105         }
106       else
107           caf_runtime_error (msg);
108     }
109
110   if (stat)
111     *stat = 0;
112
113   if (type == CAF_REGTYPE_COARRAY_STATIC)
114     {
115       caf_static_t *tmp = malloc (sizeof (caf_static_t));
116       tmp->prev  = caf_static_list;
117       tmp->token = token;
118       caf_static_list = tmp;
119     }
120   return local;
121 }
122
123
124 int
125 _gfortran_caf_deregister (void **token __attribute__ ((unused)))
126 {
127   return 0;
128 }
129
130
131 void
132 _gfortran_caf_sync_all (int *stat,
133                         char *errmsg __attribute__ ((unused)),
134                         int errmsg_len __attribute__ ((unused)))
135 {
136   if (stat)
137     *stat = 0;
138 }
139
140
141 void
142 _gfortran_caf_sync_images (int count __attribute__ ((unused)),
143                            int images[] __attribute__ ((unused)),
144                            int *stat,
145                            char *errmsg __attribute__ ((unused)),
146                            int errmsg_len __attribute__ ((unused)))
147 {
148 #ifdef GFC_CAF_CHECK
149   int i;
150
151   for (i = 0; i < count; i++)
152     if (images[i] != 1)
153       {
154         fprintf (stderr, "COARRAY ERROR: Invalid image index %d to SYNC "
155                  "IMAGES", images[i]);
156         exit (EXIT_FAILURE);
157       }
158 #endif
159
160   if (stat)
161     *stat = 0;
162 }
163
164
165 void
166 _gfortran_caf_error_stop_str (const char *string, int32_t len)
167 {
168   fputs ("ERROR STOP ", stderr);
169   while (len--)
170     fputc (*(string++), stderr);
171   fputs ("\n", stderr);
172
173   exit (1);
174 }
175
176
177 void
178 _gfortran_caf_error_stop (int32_t error)
179 {
180   fprintf (stderr, "ERROR STOP %d\n", error);
181   exit (error);
182 }