static void tcp_call( final AutoBuffer ab ) { int port = ab.getPort(); long[] snap = ab.getA8(); int idx = CLOUD.nidx(ab._h2o); if( idx >= 0 && idx < SNAPSHOT.length ) SNAPSHOT[idx] = snap; // Ignore out-of-cloud timelines ab.close(); synchronized(TimeLine.class) { TimeLine.class.notify(); } }
@Override public AutoBuffer call( AutoBuffer ab ) { long[] a = snapshot(); if( ab._h2o == H2O.SELF ) { synchronized(TimeLine.class) { for( int i=0; i<CLOUD._memary.length; i++ ) if( CLOUD._memary[i]==H2O.SELF ) SNAPSHOT[i] = a; TimeLine.class.notify(); } return null; // No I/O needed for my own snapshot } // Send timeline to remote while( true ) { AutoBuffer tab = new AutoBuffer(ab._h2o); try { tab.putUdp(UDP.udp.timeline).putA8(a).close(); return null; } catch( AutoBuffer.AutoBufferException tue ) { tab.close(); } } }
protected int response( AutoBuffer ab ) { assert _tasknum==ab.getTask(); if( _done ) return ab.close(); // Ignore duplicate response packet int flag = ab.getFlag(); // Must read flag also, to advance ab if( flag == SERVER_TCP_SEND ) return ab.close(); // Ignore UDP packet for a TCP reply assert flag == SERVER_UDP_SEND; synchronized(this) { // Install the answer under lock if( _done ) return ab.close(); // Ignore duplicate response packet UDPTimeOutThread.PENDING.remove(this); _dt.read(ab); // Read the answer (under lock?) _size_rez = ab.size(); // Record received size ab.close(); // Also finish the read (under lock?) _dt.onAck(); // One time only execute (before sending ACKACK) _done = true; // Only read one (of many) response packets ab._h2o.taskRemove(_tasknum); // Flag as task-completed, even if the result is null notifyAll(); // And notify in any case } doAllCompletions(); // Send all tasks needing completion to the work queues return 0; }
@Override public byte[] load(Value v) { File f = getFile(v); if( f.length() < v._max ) { // Should be fully on disk... // or it's a racey delete of a spilled value assert !v.isPersisted() : f.length() + " " + v._max + " " + v._key; return null; // No value } try { FileInputStream s = new FileInputStream(f); try { AutoBuffer ab = new AutoBuffer(s.getChannel(), true, Value.ICE); byte[] b = ab.getA1(v._max); ab.close(); return b; } finally { s.close(); } } catch( IOException e ) { // Broken disk / short-file??? throw new RuntimeException(Log.err("File load failed: ", e)); } }
static void build_and_multicast( H2O cloud, HeartBeat hb ) { // Paxos.print_debug("send: heartbeat ",cloud._memset); assert hb._cloud_hash != 0; // Set before send, please H2O.SELF._heartbeat = hb; hb.write(new AutoBuffer(H2O.SELF).putUdp(UDP.udp.heartbeat)).close(); } }
@Override public void save(Model m, File f) throws IOException { assert m!=null : "Model cannot be null!"; FileOutputStream fo = null; AutoBuffer ab = null; try { fo = new FileOutputStream(f); m.getModelSerializer().save(m, saveHeader( m, ab=ab4write(fo.getChannel()) ) ); } catch( FileNotFoundException e ) { throw new IllegalArgumentException("Cannot open given file!", e); } finally { if (ab!=null) ab.close(); Utils.close(fo); } }
new AutoBuffer(H2O.SELF).putUdp(udp.timeline).close();
public void send(H2ONode target) { assert this != none; new AutoBuffer(target).putUdp(udp.rebooted).put1(ordinal()).close(); } public void broadcast() { send(H2O.SELF); }
@Override public Model load(File f) throws IOException { FileInputStream fi = null; AutoBuffer ab = null; Model m = null; try { fi = new FileInputStream(f); m = loadHeader(ab=ab4read(fi.getChannel())); m.getModelSerializer().load(m, ab); if (m._key!=null) { DKV.put(m._key, m); } } catch( FileNotFoundException e ) { throw new IllegalArgumentException("Cannot open given file!", e); } finally { if (ab!=null) ab.close(); Utils.close(fi); } return m; }
@Override public byte[] load(Value v) { long skip = 0; Key k = v._key; // Convert a chunk into a long-offset from the base file. if( k._kb[0] == Key.DVEC ) skip = water.fvec.NFSFileVec.chunkOffset(k); // The offset try { FileInputStream s = null; try { s = new FileInputStream(getFileForKey(k)); FileChannel fc = s.getChannel(); fc.position(skip); AutoBuffer ab = new AutoBuffer(fc, true, Value.NFS); byte[] b = ab.getA1(v._max); ab.close(); assert v.isPersisted(); return b; } finally { if( s != null ) s.close(); } } catch( IOException e ) { // Broken disk / short-file??? H2O.ignore(e); return null; } }
@Override public void store(Value v) { // Only the home node does persistence on NFS if( !v._key.home() ) return; // A perhaps useless cutout: the upper layers should test this first. if( v.isPersisted() ) return; try { File f = getFileForKey(v._key); f.mkdirs(); FileOutputStream s = new FileOutputStream(f); try { byte[] m = v.memOrLoad(); assert (m == null || m.length == v._max); // Assert not saving partial files if( m != null ) new AutoBuffer(s.getChannel(), false, Value.NFS).putA1(m, m.length).close(); v.setdsk(); // Set as write-complete to disk } finally { s.close(); } } catch( IOException e ) { H2O.ignore(e); } }
@Override public void compute2() { _ab.getPort(); // skip past the port if( _ctrl <= UDP.udp.ack.ordinal() ) UDP.udp.UDPS[_ctrl]._udp.call(_ab).close(); else RPC.remote_exec(_ab); tryComplete(); } /** Exceptional completion path; mostly does printing if the exception was
@Override public void store(Value v) { assert !v.isPersisted(); new File(_dir, getIceDirectory(v._key)).mkdirs(); // Nuke any prior file. FileOutputStream s = null; try { s = new FileOutputStream(getFile(v)); } catch( FileNotFoundException e ) { String info = "Key: " + v._key.toString() + "\nEncoded: " + getFile(v); throw new RuntimeException(Log.err("Encoding a key to a file failed!\n" + info, e)); } try { byte[] m = v.memOrLoad(); // we are not single threaded anymore assert m != null && m.length == v._max : "Trying to save partial file: value key=" + v._key + ", length to save=" + m + ", value max size=" + v._max; // Assert not saving partial files new AutoBuffer(s.getChannel(), false, Value.ICE).putA1(m, m.length).close(); v.setdsk(); // Set as write-complete to disk } finally { Utils.close(s); } }
AutoBuffer call(AutoBuffer ab) { int tnum = ab.getTask(); RPC<?> t = ab._h2o.taskGet(tnum); assert t== null || t._tasknum == tnum; if( t != null ) t.response(ab); // Do the 2nd half of this task, includes ACKACK else ab.close(); // Else forgotten task, but still must ACKACK return new AutoBuffer(ab._h2o).putTask(UDP.udp.ackack.ordinal(),tnum); }
final void resend_ack() { assert _computedAndReplied : "Found RPCCall not computed "+_tsknum; DTask dt = _dt; if( dt == null ) return; // Received ACKACK already UDP.udp udp = dt.priority()==H2O.FETCH_ACK_PRIORITY ? UDP.udp.fetchack : UDP.udp.ack; AutoBuffer rab = new AutoBuffer(_client).putTask(udp,_tsknum); boolean wasTCP = dt._repliedTcp; if( wasTCP ) rab.put1(RPC.SERVER_TCP_SEND) ; // Original reply sent via TCP else dt.write(rab.put1(RPC.SERVER_UDP_SEND)); // Original reply sent via UDP assert sz_check(rab) : "Resend of "+_dt.getClass()+" changes size from "+_size+" to "+rab.size(); assert dt._repliedTcp==wasTCP; rab.close(); // Double retry until we exceed existing age. This is the time to delay // until we try again. Note that we come here immediately on creation, // so the first doubling happens before anybody does any waiting. Also // note the generous 5sec cap: ping at least every 5 sec. _retry += (_retry < 5000 ) ? _retry : 5000; } @Override public byte priority() { return _dt.priority(); }
ab.close(); // Then close; send final byte _computedAndReplied = true; // After the final handshake, set computed+replied bit break; // Break out of retry loop
_unknown_packet_time = ab._h2o._last_heard_from; ab.close();
new AutoBuffer(ab._h2o).putTask(UDP.udp.ackack.ordinal(),task).close();
dinfo.writeAll(new AutoBuffer(baos, true)).close(); baos.close();
old.resend_ack(); ab.close();