68 #else
69
70 /* This gets us the new structured proc interfaces of 5.6 & later */
71 /* - see comment in <sys/procfs.h> */
72 #define _STRUCTURED_PROC 1
73 #include <sys/procfs.h>
74
75 #endif /* _ALLBSD_SOURCE */
76
77 #if defined(_AIX)
78 #define DIR DIR64
79 #define dirent dirent64
80 #define opendir opendir64
81 #define readdir readdir64
82 #define closedir closedir64
83 #endif
84
85 // true = get available swap in bytes
86 // false = get total swap in bytes
87 static jlong get_total_or_available_swap_space_size(JNIEnv* env, jboolean available) {
88 #ifdef __solaris__
89 long total, avail;
90 int nswap, i, count;
91 swaptbl_t *stbl;
92 char *strtab;
93
94 // First get the number of swap resource entries
95 if ((nswap = swapctl(SC_GETNSWP, NULL)) == -1) {
96 throw_internal_error(env, "swapctl failed to get nswap");
97 return -1;
98 }
99 if (nswap == 0) {
100 return 0;
101 }
102
103 // Allocate storage for resource entries
104 stbl = (swaptbl_t*) malloc(nswap * sizeof(swapent_t) +
105 sizeof(struct swaptable));
106 if (stbl == NULL) {
107 JNU_ThrowOutOfMemoryError(env, 0);
108 return -1;
109 }
110
111 // Allocate storage for the table
112 strtab = (char*) malloc((nswap + 1) * MAXPATHLEN);
113 if (strtab == NULL) {
114 free(stbl);
115 JNU_ThrowOutOfMemoryError(env, 0);
116 return -1;
117 }
118
119 for (i = 0; i < (nswap + 1); i++) {
120 stbl->swt_ent[i].ste_path = strtab + (i * MAXPATHLEN);
121 }
122 stbl->swt_n = nswap + 1;
123
124 // Get the entries
125 if ((count = swapctl(SC_LIST, stbl)) < 0) {
126 free(stbl);
127 free(strtab);
128 throw_internal_error(env, "swapctl failed to get swap list");
129 return -1;
130 }
131
132 // Sum the entries to get total and free swap
133 total = 0;
134 avail = 0;
135 for (i = 0; i < count; i++) {
136 total += stbl->swt_ent[i].ste_pages;
137 avail += stbl->swt_ent[i].ste_free;
138 }
139
140 free(stbl);
141 free(strtab);
142 return available ? ((jlong)avail * page_size) :
143 ((jlong)total * page_size);
144 #elif defined(__linux__)
145 int ret;
146 FILE *fp;
147 jlong total = 0, avail = 0;
148
149 struct sysinfo si;
150 ret = sysinfo(&si);
151 if (ret != 0) {
152 throw_internal_error(env, "sysinfo failed to get swap size");
153 }
154 total = (jlong)si.totalswap * si.mem_unit;
155 avail = (jlong)si.freeswap * si.mem_unit;
156
157 return available ? avail : total;
158 #elif defined(__APPLE__)
159 struct xsw_usage vmusage;
160 size_t size = sizeof(vmusage);
161 if (sysctlbyname("vm.swapusage", &vmusage, &size, NULL, 0) != 0) {
162 throw_internal_error(env, "sysctlbyname failed");
163 }
164 return available ? (jlong)vmusage.xsu_avail : (jlong)vmusage.xsu_total;
166 /*
167 * XXXBSD: there's no way available to get swap info in
168 * FreeBSD. Usage of libkvm is not an option here
169 */
170 // throw_internal_error(env, "Unimplemented in FreeBSD");
171 return (0);
172 #endif
173 }
174
175 JNIEXPORT void JNICALL
176 Java_com_sun_management_internal_OperatingSystemImpl_initialize0
177 (JNIEnv *env, jclass cls)
178 {
179 page_size = sysconf(_SC_PAGESIZE);
180 }
181
182 JNIEXPORT jlong JNICALL
183 Java_com_sun_management_internal_OperatingSystemImpl_getCommittedVirtualMemorySize0
184 (JNIEnv *env, jobject mbean)
185 {
186 #ifdef __solaris__
187 psinfo_t psinfo;
188 ssize_t result;
189 size_t remaining;
190 char* addr;
191 int fd;
192
193 fd = open64("/proc/self/psinfo", O_RDONLY, 0);
194 if (fd < 0) {
195 throw_internal_error(env, "Unable to open /proc/self/psinfo");
196 return -1;
197 }
198
199 addr = (char *)&psinfo;
200 for (remaining = sizeof(psinfo_t); remaining > 0;) {
201 result = read(fd, addr, remaining);
202 if (result < 0) {
203 if (errno != EINTR) {
204 close(fd);
205 throw_internal_error(env, "Unable to read /proc/self/psinfo");
206 return -1;
207 }
208 } else {
209 remaining -= result;
210 addr += result;
211 }
212 }
213
214 close(fd);
215 return (jlong) psinfo.pr_size * 1024;
216 #elif defined(__linux__)
217 FILE *fp;
218 unsigned long vsize = 0;
219
220 if ((fp = fopen("/proc/self/stat", "r")) == NULL) {
221 throw_internal_error(env, "Unable to open /proc/self/stat");
222 return -1;
223 }
224
225 // Ignore everything except the vsize entry
226 if (fscanf(fp, "%*d %*s %*c %*d %*d %*d %*d %*d %*u %*u %*u %*u %*u %*d %*d %*d %*d %*d %*d %*u %*u %*d %lu %*[^\n]\n", &vsize) == EOF) {
227 throw_internal_error(env, "Unable to get virtual memory usage");
228 fclose(fp);
229 return -1;
230 }
231
232 fclose(fp);
233 return (jlong)vsize;
234 #elif defined(__APPLE__)
235 struct task_basic_info t_info;
236 mach_msg_type_number_t t_info_count = TASK_BASIC_INFO_COUNT;
269 {
270 #ifdef __APPLE__
271 struct rusage usage;
272 if (getrusage(RUSAGE_SELF, &usage) != 0) {
273 throw_internal_error(env, "getrusage failed");
274 return -1;
275 }
276 jlong microsecs =
277 usage.ru_utime.tv_sec * 1000 * 1000 + usage.ru_utime.tv_usec +
278 usage.ru_stime.tv_sec * 1000 * 1000 + usage.ru_stime.tv_usec;
279 return microsecs * 1000;
280 #else
281 jlong clk_tck, ns_per_clock_tick;
282 jlong cpu_time_ns;
283 struct tms time;
284
285 /*
286 * BSDNOTE: FreeBSD implements _SC_CLK_TCK since FreeBSD 5, so
287 * add a magic to handle it
288 */
289 #if defined(__solaris__) || defined(_SC_CLK_TCK)
290 clk_tck = (jlong) sysconf(_SC_CLK_TCK);
291 #elif defined(__linux__) || defined(_ALLBSD_SOURCE)
292 clk_tck = 100;
293 #endif
294 if (clk_tck == -1) {
295 throw_internal_error(env,
296 "sysconf failed - not able to get clock tick");
297 return -1;
298 }
299
300 times(&time);
301 ns_per_clock_tick = (jlong) 1000 * 1000 * 1000 / (jlong) clk_tck;
302 cpu_time_ns = ((jlong)time.tms_utime + (jlong) time.tms_stime) *
303 ns_per_clock_tick;
304 return cpu_time_ns;
305 #endif
306 }
307
308 JNIEXPORT jlong JNICALL
309 Java_com_sun_management_internal_OperatingSystemImpl_getFreeMemorySize0
|
68 #else
69
70 /* This gets us the new structured proc interfaces of 5.6 & later */
71 /* - see comment in <sys/procfs.h> */
72 #define _STRUCTURED_PROC 1
73 #include <sys/procfs.h>
74
75 #endif /* _ALLBSD_SOURCE */
76
77 #if defined(_AIX)
78 #define DIR DIR64
79 #define dirent dirent64
80 #define opendir opendir64
81 #define readdir readdir64
82 #define closedir closedir64
83 #endif
84
85 // true = get available swap in bytes
86 // false = get total swap in bytes
87 static jlong get_total_or_available_swap_space_size(JNIEnv* env, jboolean available) {
88 #if defined(__linux__)
89 int ret;
90 FILE *fp;
91 jlong total = 0, avail = 0;
92
93 struct sysinfo si;
94 ret = sysinfo(&si);
95 if (ret != 0) {
96 throw_internal_error(env, "sysinfo failed to get swap size");
97 }
98 total = (jlong)si.totalswap * si.mem_unit;
99 avail = (jlong)si.freeswap * si.mem_unit;
100
101 return available ? avail : total;
102 #elif defined(__APPLE__)
103 struct xsw_usage vmusage;
104 size_t size = sizeof(vmusage);
105 if (sysctlbyname("vm.swapusage", &vmusage, &size, NULL, 0) != 0) {
106 throw_internal_error(env, "sysctlbyname failed");
107 }
108 return available ? (jlong)vmusage.xsu_avail : (jlong)vmusage.xsu_total;
110 /*
111 * XXXBSD: there's no way available to get swap info in
112 * FreeBSD. Usage of libkvm is not an option here
113 */
114 // throw_internal_error(env, "Unimplemented in FreeBSD");
115 return (0);
116 #endif
117 }
118
119 JNIEXPORT void JNICALL
120 Java_com_sun_management_internal_OperatingSystemImpl_initialize0
121 (JNIEnv *env, jclass cls)
122 {
123 page_size = sysconf(_SC_PAGESIZE);
124 }
125
126 JNIEXPORT jlong JNICALL
127 Java_com_sun_management_internal_OperatingSystemImpl_getCommittedVirtualMemorySize0
128 (JNIEnv *env, jobject mbean)
129 {
130 #if defined(__linux__)
131 FILE *fp;
132 unsigned long vsize = 0;
133
134 if ((fp = fopen("/proc/self/stat", "r")) == NULL) {
135 throw_internal_error(env, "Unable to open /proc/self/stat");
136 return -1;
137 }
138
139 // Ignore everything except the vsize entry
140 if (fscanf(fp, "%*d %*s %*c %*d %*d %*d %*d %*d %*u %*u %*u %*u %*u %*d %*d %*d %*d %*d %*d %*u %*u %*d %lu %*[^\n]\n", &vsize) == EOF) {
141 throw_internal_error(env, "Unable to get virtual memory usage");
142 fclose(fp);
143 return -1;
144 }
145
146 fclose(fp);
147 return (jlong)vsize;
148 #elif defined(__APPLE__)
149 struct task_basic_info t_info;
150 mach_msg_type_number_t t_info_count = TASK_BASIC_INFO_COUNT;
183 {
184 #ifdef __APPLE__
185 struct rusage usage;
186 if (getrusage(RUSAGE_SELF, &usage) != 0) {
187 throw_internal_error(env, "getrusage failed");
188 return -1;
189 }
190 jlong microsecs =
191 usage.ru_utime.tv_sec * 1000 * 1000 + usage.ru_utime.tv_usec +
192 usage.ru_stime.tv_sec * 1000 * 1000 + usage.ru_stime.tv_usec;
193 return microsecs * 1000;
194 #else
195 jlong clk_tck, ns_per_clock_tick;
196 jlong cpu_time_ns;
197 struct tms time;
198
199 /*
200 * BSDNOTE: FreeBSD implements _SC_CLK_TCK since FreeBSD 5, so
201 * add a magic to handle it
202 */
203 #if defined(_SC_CLK_TCK)
204 clk_tck = (jlong) sysconf(_SC_CLK_TCK);
205 #elif defined(__linux__) || defined(_ALLBSD_SOURCE)
206 clk_tck = 100;
207 #endif
208 if (clk_tck == -1) {
209 throw_internal_error(env,
210 "sysconf failed - not able to get clock tick");
211 return -1;
212 }
213
214 times(&time);
215 ns_per_clock_tick = (jlong) 1000 * 1000 * 1000 / (jlong) clk_tck;
216 cpu_time_ns = ((jlong)time.tms_utime + (jlong) time.tms_stime) *
217 ns_per_clock_tick;
218 return cpu_time_ns;
219 #endif
220 }
221
222 JNIEXPORT jlong JNICALL
223 Java_com_sun_management_internal_OperatingSystemImpl_getFreeMemorySize0
|