def sendPing(self, pn, i_req, ack_key=None):
        # Transmit a single ping to the given node

        osm = self.main.osm

        # Expire old ack requests
        if pn.ping_reqs:
            now = seconds()
            for req_key, when in pn.ping_reqs.items():
                if now - when > 15.0:
                    del pn.ping_reqs[req_key]

        iwant = pn.outbound

        # For now, include neighbor list only when requesting an ack.
        nblist = i_req

        # Offline bit is set if this neighbor is not recognized.
        # (this just gets ignored, but it could be useful someday)
        offline = osm.syncd and (pn.ipp not in osm.lookup_ipp)

        # Build packet
        packet = ['PG']
        packet.append(osm.me.ipp)

        flags = ((iwant and IWANT_BIT)       |
                 (pn.got_ack and GOTACK_BIT) |
                 (i_req and REQ_BIT)         |
                 (bool(ack_key) and ACK_BIT) |
                 (nblist and NBLIST_BIT)     |
                 (offline and OFFLINE_BIT)
                 )

        packet.append(struct.pack('!B', flags))

        if i_req:
            # I'm requesting that this packet be acknowledged, so generate
            # a new req_key
            while True:
                req_key = randbytes(4)
                if req_key not in pn.ping_reqs:
                    break

            pn.ping_reqs[req_key] = seconds()
            packet.append(req_key)

        if ack_key:
            packet.append(ack_key)

        if nblist:
            if osm.syncd:
                # Grab my list of ping neighbors.
                nbs = [pn_it.ipp for pn_it in self.pnbs.itervalues()
                       if (pn_it.ipp != pn.ipp and
                           pn_it.ipp in osm.lookup_ipp and
                           pn_it.stronglyConnected())]

                # Don't bother sending more than 8
                nbs.sort()
                del nbs[8:]
            else:
                nbs = []

            packet.append(struct.pack("!B", len(nbs)))
            packet.extend(nbs)

        ad = Ad().setRawIPPort(pn.ipp)
        self.main.ph.sendPacket(''.join(packet), ad.getAddrTuple())