GRASS GIS 8 Programmer's Manual  8.5.0dev(2025)-d3092090e5
All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
mask_info.c
Go to the documentation of this file.
1 /**
2  * \file lib/raster/mask_info.c
3  *
4  * \brief Raster Library - Get mask information
5  *
6  * (C) 1999-2024 by Vaclav Petras and the GRASS Development Team
7  *
8  * This program is free software under the GNU General Public
9  * License (>=v2). Read the file COPYING that comes with GRASS
10  * for details.
11  *
12  * \author CERL
13  * \author Vaclav Petras, NC State University, Center for Geospatial Analytics
14  */
15 
16 #include <string.h>
17 #include <stdbool.h>
18 #include <stdlib.h>
19 
20 #if defined(_OPENMP)
21 #include <omp.h>
22 #endif
23 
24 #include <grass/gis.h>
25 #include <grass/raster.h>
26 #include <grass/glocale.h>
27 
28 /**
29  * @brief Get a printable text with information about raster mask
30  *
31  * Determines if 2D raster mask is present and returns textual information about
32  * the mask suitable for end-user display. The resulting text is translated.
33  * Caller is responsible for freeing the memory of the returned string.
34  *
35  * @return New string with textual information
36  *
37  * @see Rast_mask_status()
38  */
39 char *Rast_mask_info(void)
40 {
41  char text[GNAME_MAX + GMAPSET_MAX + 16];
42  char name[GNAME_MAX];
43  char mapset[GMAPSET_MAX];
44 
45  switch (Rast__mask_info(name, mapset)) {
46  case 1:
47  snprintf(text, sizeof(text), _("<%s> in mapset <%s>"), name, mapset);
48  break;
49  case -1:
50  strcpy(text, _("none"));
51  break;
52  default:
53  strcpy(text, _("not known"));
54  break;
55  }
56 
57  return G_store(text);
58 }
59 
60 /**
61  * @brief Retrieves the name of the raster mask to use.
62  *
63  * The returned raster map name is fully qualified, i.e., in the form
64  * "name@mapset". The mask name is returned whether the mask is present or not.
65  *
66  * This function checks if an environment variable "GRASS_MASK" is set.
67  * If it is set, the value of the environment variable is returned
68  * as the mask name. If it is not set, the function will default to the
69  * mask name "MASK@<mapset>", where <mapset> is the current mapset.
70  *
71  * The memory for the returned mask name is dynamically allocated using
72  * G_store(). It is the caller's responsibility to free the memory with
73  * G_free() when it is no longer needed.
74  *
75  * @returns A dynamically allocated string containing the mask name.
76  */
77 char *Rast_mask_name(void)
78 {
79  // First, see if the environment variable is defined.
80  const char *env_variable = getenv("GRASS_MASK");
81  if (env_variable != NULL && strcmp(env_variable, "") != 0) {
82  // Variable exists and is not empty.
83  // While the function does not document that, the provided mapset
84  // is a fallback, so we don't have to parse the name to find out
85  // ourselves what to do.
86  return G_fully_qualified_name(env_variable, G_mapset());
87  }
88 
89  // Mask name defaults to "MASK@<current mapset>".
90  return G_fully_qualified_name("MASK", G_mapset());
91 }
92 
93 /**
94  * @brief Get name of a mask if it is present
95  *
96  * Unlike, Rast__mask_info() this always returns name of the mask
97  * if it is present regardless of the mask being a reclass or not.
98  *
99  * @param[out] name Name of the raster map used as mask
100  * @param[out] mapset Name of the map's mapset
101  *
102  * @return true if mask is present, false otherwise
103  */
104 static bool Rast__get_present_mask(char *name, char *mapset)
105 {
106  char rname[GNAME_MAX], rmapset[GMAPSET_MAX];
107  char *full_name = Rast_mask_name();
108  if (!G_find_raster2(full_name, ""))
109  return false;
110  G_unqualified_name(full_name, "", rname, rmapset);
111  strncpy(name, rname, GMAPSET_MAX);
112  strncpy(mapset, rmapset, GMAPSET_MAX);
113  G_free(full_name);
114  return true;
115 }
116 
117 /**
118  * @brief Get raster mask status information
119  *
120  * _is_mask_reclass_ is a pointer to a bool variable which
121  * will be set to true if mask raster is a reclass and false otherwise.
122  *
123  * If you are not interested in the underlying reclassified raster map,
124  * pass NULL pointers for the three reclass parameters:
125  *
126  * ```
127  * Rast_mask_status(name, mapset, NULL, NULL, NULL);
128  * ```
129  *
130  * @param[out] name Name of the raster map used as mask
131  * @param[out] mapset Name of the mapset the raster is in
132  * @param[out] is_mask_reclass Will be set to true if mask raster is a reclass
133  * @param[out] reclass_name Name of the underlying reclassified raster map
134  * @param[out] reclass_mapset Name of the mapset the reclassified raster is in
135  *
136  * @return true if mask is present, false otherwise
137  */
138 bool Rast_mask_status(char *name, char *mapset, bool *is_mask_reclass,
139  char *reclass_name, char *reclass_mapset)
140 {
141  bool present = Rast__get_present_mask(name, mapset);
142 
143  if (is_mask_reclass && reclass_name && reclass_mapset) {
144  if (present) {
145  *is_mask_reclass =
146  Rast_is_reclass(name, mapset, reclass_name, reclass_mapset) > 0;
147  }
148  else {
149  *is_mask_reclass = false;
150  }
151  }
152  return present;
153 }
154 
155 /**
156  * @brief Get information about the current mask
157  *
158  * Determines the status of the automatic masking and the name of the 2D
159  * raster which forms the mask. Typically, mask is raster called MASK in the
160  * current mapset, but when used with r.mask, it is usually a reclassed
161  * raster, and so when a mask raster is present and it is a reclass raster,
162  * the name and mapset of the underlying reclassed raster are returned.
163  *
164  * The name and mapset is written to the parameter which need to be defined
165  * with a sufficient size, least as `char name[GNAME_MAX], mapset[GMAPSET_MAX]`.
166  *
167  * When the masking is not active, -1 is returned and name and mapset are
168  * undefined. When the masking is active, 1 is returned and name and mapset
169  * will hold the name and mapset of the underlying raster.
170  *
171  * @param[out] name Name of the raster map used as mask
172  * @param[out] mapset Name of the map's mapset
173  *
174  * @return 1 if mask is present, -1 otherwise
175  *
176  * @see Rast_mask_status(), Rast_mask_name()
177  */
178 int Rast__mask_info(char *name, char *mapset)
179 {
180  char rname[GNAME_MAX], rmapset[GMAPSET_MAX];
181  bool present = Rast__get_present_mask(name, mapset);
182  if (!present)
183  return -1;
184 
185  if (Rast_is_reclass(name, mapset, rname, rmapset) > 0) {
186  strcpy(name, rname);
187  strcpy(mapset, rmapset);
188  }
189  return 1;
190 }
191 
192 /**
193  * @brief Check presence of 2D raster mask
194  *
195  * @return true if mask is present, false otherwise
196  */
198 {
199  char *name = Rast_mask_name();
200  bool present = G_find_raster2(name, "") != NULL;
201  return present;
202 }
203 
204 /**
205  * \brief Disable OpenMP if raster mask is present
206  *
207  * This helper function can be removed when raster reading is made
208  * thread safe.
209  *
210  * \param nprocs number of threads to use
211  * \return number of threads in use
212  */
214 {
215 
216 #if defined(_OPENMP)
217  if (nprocs > 1 && Rast_mask_is_present()) {
218  omp_set_num_threads(1);
219  G_verbose_message(_("Single thread processing enforced due to "
220  "raster mask being present."));
221  nprocs = 1;
222  }
223 #else
224  nprocs = 1;
225 #endif
226 
227  return nprocs;
228 }
#define NULL
Definition: ccmath.h:32
void G_free(void *)
Free allocated memory.
Definition: gis/alloc.c:150
int G_unqualified_name(const char *, const char *, char *, char *)
Returns unqualified map name (without @ mapset)
Definition: nme_in_mps.c:134
const char * G_find_raster2(const char *, const char *)
Find a raster map (look but don't touch)
Definition: find_rast.c:76
void void G_verbose_message(const char *,...) __attribute__((format(printf
const char * G_mapset(void)
Get current mapset name.
Definition: gis/mapset.c:33
char * G_fully_qualified_name(const char *, const char *)
Get fully qualified element name.
Definition: nme_in_mps.c:101
char * G_store(const char *)
Copy string to allocated memory.
Definition: strings.c:87
int Rast_is_reclass(const char *, const char *, char *, char *)
Check if raster map is reclassified.
Definition: reclass.c:43
#define GMAPSET_MAX
Definition: gis.h:197
#define GNAME_MAX
Definition: gis.h:196
#define _(str)
Definition: glocale.h:10
int Rast_disable_omp_on_mask(int nprocs)
Disable OpenMP if raster mask is present.
Definition: mask_info.c:213
char * Rast_mask_name(void)
Retrieves the name of the raster mask to use.
Definition: mask_info.c:77
bool Rast_mask_status(char *name, char *mapset, bool *is_mask_reclass, char *reclass_name, char *reclass_mapset)
Get raster mask status information.
Definition: mask_info.c:138
char * Rast_mask_info(void)
Get a printable text with information about raster mask.
Definition: mask_info.c:39
int Rast__mask_info(char *name, char *mapset)
Get information about the current mask.
Definition: mask_info.c:178
bool Rast_mask_is_present(void)
Check presence of 2D raster mask.
Definition: mask_info.c:197
const char * name
Definition: named_colr.c:6
#define strcpy
Definition: parson.c:62