001// Copyright (c) FIRST and other WPILib contributors. 002// Open Source Software; you can modify and/or share it under the terms of 003// the WPILib BSD license file in the root directory of this project. 004 005package org.wpilib.util; 006 007import java.io.IOException; 008import java.nio.ByteBuffer; 009import java.util.concurrent.atomic.AtomicBoolean; 010import org.wpilib.util.runtime.RuntimeLoader; 011 012/** WPIUtil JNI. */ 013public class WPIUtilJNI { 014 static boolean libraryLoaded = false; 015 016 /** Sets whether JNI should be loaded in the static block. */ 017 public static class Helper { 018 private static AtomicBoolean extractOnStaticLoad = new AtomicBoolean(true); 019 020 /** 021 * Returns true if the JNI should be loaded in the static block. 022 * 023 * @return True if the JNI should be loaded in the static block. 024 */ 025 public static boolean getExtractOnStaticLoad() { 026 return extractOnStaticLoad.get(); 027 } 028 029 /** 030 * Sets whether the JNI should be loaded in the static block. 031 * 032 * @param load Whether the JNI should be loaded in the static block. 033 */ 034 public static void setExtractOnStaticLoad(boolean load) { 035 extractOnStaticLoad.set(load); 036 } 037 038 /** Utility class. */ 039 private Helper() {} 040 } 041 042 static { 043 if (Helper.getExtractOnStaticLoad()) { 044 try { 045 RuntimeLoader.loadLibrary("wpiutiljni"); 046 } catch (Exception ex) { 047 ex.printStackTrace(); 048 System.exit(1); 049 } 050 libraryLoaded = true; 051 } 052 } 053 054 /** 055 * Force load the library. 056 * 057 * @throws IOException if the library failed to load 058 */ 059 public static synchronized void forceLoad() throws IOException { 060 if (libraryLoaded) { 061 return; 062 } 063 RuntimeLoader.loadLibrary("wpiutiljni"); 064 libraryLoaded = true; 065 } 066 067 /** Checks if the MSVC runtime is valid. Throws a runtime exception if not. */ 068 public static native void checkMsvcRuntime(); 069 070 /** 071 * Write the given string to stderr. 072 * 073 * @param str String to write. 074 */ 075 public static native void writeStderr(String str); 076 077 /** Enable mock time. */ 078 public static native void enableMockTime(); 079 080 /** Disable mock time. */ 081 public static native void disableMockTime(); 082 083 /** 084 * Set mock time. 085 * 086 * @param time The desired time in microseconds. 087 */ 088 public static native void setMockTime(long time); 089 090 /** 091 * Returns the time. 092 * 093 * @return The time. 094 */ 095 public static native long now(); 096 097 /** 098 * Returns the system time. 099 * 100 * @return The system time. 101 */ 102 public static native long getSystemTime(); 103 104 /** 105 * Creates an event. Events have binary state (signaled or not signaled) and may be either 106 * automatically reset or manually reset. Automatic-reset events go to non-signaled state when a 107 * WaitForObject is woken up by the event; manual-reset events require ResetEvent() to be called 108 * to set the event to non-signaled state; if ResetEvent() is not called, any waiter on that event 109 * will immediately wake when called. 110 * 111 * @param manualReset true for manual reset, false for automatic reset 112 * @param initialState true to make the event initially in signaled state 113 * @return Event handle 114 */ 115 public static native int createEvent(boolean manualReset, boolean initialState); 116 117 /** 118 * Destroys an event. Destruction wakes up any waiters. 119 * 120 * @param eventHandle event handle 121 */ 122 public static native void destroyEvent(int eventHandle); 123 124 /** 125 * Sets an event to signaled state. 126 * 127 * @param eventHandle event handle 128 */ 129 public static native void setEvent(int eventHandle); 130 131 /** 132 * Sets an event to non-signaled state. 133 * 134 * @param eventHandle event handle 135 */ 136 public static native void resetEvent(int eventHandle); 137 138 /** 139 * Creates a semaphore. Semaphores keep an internal counter. Releasing the semaphore increases the 140 * count. A semaphore with a non-zero count is considered signaled. When a waiter wakes up it 141 * atomically decrements the count by 1. This is generally useful in a single-supplier, 142 * multiple-consumer scenario. 143 * 144 * @param initialCount initial value for the semaphore's internal counter 145 * @param maximumCount maximum value for the semaphore's internal counter 146 * @return Semaphore handle 147 */ 148 public static native int createSemaphore(int initialCount, int maximumCount); 149 150 /** 151 * Destroys a semaphore. Destruction wakes up any waiters. 152 * 153 * @param semHandle semaphore handle 154 */ 155 public static native void destroySemaphore(int semHandle); 156 157 /** 158 * Releases N counts of a semaphore. 159 * 160 * @param semHandle semaphore handle 161 * @param releaseCount amount to add to semaphore's internal counter; must be positive 162 * @return True on successful release, false on failure (e.g. release count would exceed maximum 163 * value, or handle invalid) 164 */ 165 public static native boolean releaseSemaphore(int semHandle, int releaseCount); 166 167 static native long allocateRawFrame(); 168 169 static native void freeRawFrame(long frame); 170 171 static native long getRawFrameDataPtr(long frame); 172 173 static native void setRawFrameData( 174 long frame, ByteBuffer data, int size, int width, int height, int stride, int pixelFormat); 175 176 static native void setRawFrameInfo( 177 long frame, int size, int width, int height, int stride, int pixelFormat); 178 179 static native void setRawFrameTime(long frame, long timestamp, int timeSource); 180 181 /** 182 * Waits for a handle to be signaled. 183 * 184 * @param handle handle to wait on 185 * @throws InterruptedException on failure (e.g. object was destroyed) 186 */ 187 public static native void waitForObject(int handle) throws InterruptedException; 188 189 /** 190 * Waits for a handle to be signaled, with timeout. 191 * 192 * @param handle handle to wait on 193 * @param timeout timeout in seconds 194 * @return True if timeout reached without handle being signaled 195 * @throws InterruptedException on failure (e.g. object was destroyed) 196 */ 197 public static native boolean waitForObjectTimeout(int handle, double timeout) 198 throws InterruptedException; 199 200 /** 201 * Waits for one or more handles to be signaled. 202 * 203 * <p>Invalid handles are treated as signaled; the returned array will have the handle error bit 204 * set for any invalid handles. 205 * 206 * @param handles array of handles to wait on 207 * @return array of signaled handles 208 * @throws InterruptedException on failure (e.g. no objects were signaled) 209 */ 210 public static native int[] waitForObjects(int[] handles) throws InterruptedException; 211 212 /** 213 * Waits for one or more handles to be signaled, with timeout. 214 * 215 * <p>Invalid handles are treated as signaled; the returned array will have the handle error bit 216 * set for any invalid handles. 217 * 218 * @param handles array of handles to wait on 219 * @param timeout timeout in seconds 220 * @return array of signaled handles; empty if timeout reached without any handle being signaled 221 * @throws InterruptedException on failure (e.g. no objects were signaled and no timeout) 222 */ 223 public static native int[] waitForObjectsTimeout(int[] handles, double timeout) 224 throws InterruptedException; 225 226 /** Utility class. */ 227 protected WPIUtilJNI() {} 228}