import java.util.*;
import java.util.zip.*;
import java.util.List;
import java.util.regex.*;
import java.util.concurrent.*;
import java.util.concurrent.atomic.*;
import java.util.concurrent.locks.*;
import javax.swing.*;
import javax.swing.event.*;
import javax.swing.text.*;
import javax.swing.table.*;
import java.io.*;
import java.net.*;
import java.lang.reflect.*;
import java.lang.ref.*;
import java.lang.management.*;
import java.security.*;
import java.security.spec.*;
import java.awt.*;
import java.awt.event.*;
import java.awt.image.*;
import javax.imageio.*;
import java.math.*;
class main {
static class Cache {
Object maker; // func -> A
A value;
long loaded;
static boolean debug = false;
long changeCount;
Lock lock = lock();
Cache() {}
Cache(Object maker) {
this.maker = maker;}
Cache(IF0 maker) {
this.maker = maker;}
A get() {
if (hasLock(lock)) return value; // Must be called from within maker
Lock __0 = lock; lock(__0); try {
if (loaded == 0) {
value = make();
changeCount++;
loaded = sysNow();
}
return value;
} finally { unlock(__0); } }
void clear() {
Lock __1 = lock; lock(__1); try {
if (debug && loaded != 0)
print("Clearing cache");
value = null;
changeCount++;
loaded = 0;
} finally { unlock(__1); } }
// clear if older than x seconds
// 0 does not do anything
void clear(double seconds) {
Lock __2 = lock; lock(__2); try {
if (seconds != 0 && loaded != 0 && sysNow() >= loaded+seconds*1000)
clear();
} finally { unlock(__2); } }
// override
void set(A a) {
Lock __3 = lock; lock(__3); try {
value = a;
++changeCount;
loaded = sysNow();
} finally { unlock(__3); } }
A make() {
return (A) callF(maker);
}
}
static void lock(Lock lock) { try {
ping();
if (lock == null) return;
try {
lock.lockInterruptibly();
} catch (InterruptedException e) {
print("Locking interrupted! I probably deadlocked, oops.");
printStackTrace(e);
rethrow(e);
}
ping();
} catch (Exception __e) { throw rethrow(__e); } }
static void lock(Lock lock, String msg) {
print("Locking: " + msg);
lock(lock);
}
static void lock(Lock lock, String msg, long timeout) {
print("Locking: " + msg);
lockOrFail(lock, timeout);
}
static ReentrantLock lock() {
return fairLock();
}
static boolean hasLock(Lock lock) {
return ((ReentrantLock) lock).isHeldByCurrentThread();
}
static long sysNow() {
ping();
return System.nanoTime()/1000000;
}
static void unlock(Lock lock, String msg) {
if (lock == null) return;
print("Unlocking: " + msg);
lock.unlock();
}
static void unlock(Lock lock) {
if (lock == null) return;
lock.unlock();
}
static volatile StringBuffer local_log = new StringBuffer(); // not redirected
static volatile Appendable print_log = local_log; // might be redirected, e.g. to main bot
// in bytes - will cut to half that
static volatile int print_log_max = 1024*1024;
static volatile int local_log_max = 100*1024;
static boolean print_silent = false; // total mute if set
static Object print_byThread_lock = new Object();
static volatile ThreadLocal