FileDocCategorySizeDatePackage
PingSpaceMapper.javaAPI DocAzureus 3.0.3.49887Fri Jul 13 09:53:52 BST 2007com.aelitis.azureus.core.speedmanager.impl.v2

PingSpaceMapper

public class PingSpaceMapper extends Object
Classifies the ping-times and then maps them against the a grid of upload and download rates. Create a two dimensional map of upload and download rates. Map onto this space ping times. The mesh size will be smaller near zero, and larger higher up. 0 - 100 kByte/sec - 10 kBytes mesh size. 100 - 500 kBytes/sec - 50 kBytes mesh size. 500 - 5000 kBytes/sec - 100 kBytes mesh size. Anything above 5 MBytes/sec is one region.

Fields Summary
GridRegion[]
gridRegion
int
lastDownloadBitsPerSec
int
lastUploadBitsPerSec
int
goodPingInMilliSec
int
badPingInMilliSec
int
totalPointsInMap
private static final int
maxMeshIndex
public static final int
RESULT_UPLOAD_INDEX
public static final int
RESULT_DOWNLOAD_INDEX
static final int
GOOD_PING_INDEX
static final int
ANY_PING_INDEX
Constructors Summary
public PingSpaceMapper(int _goodPingInMilliSec, int _badPingInMilliSec)
Create a grid and define good and bad ping times.

param
_goodPingInMilliSec -
param
_badPingInMilliSec -


                         
        

        createNewGrid();

        goodPingInMilliSec = _goodPingInMilliSec;
        badPingInMilliSec = _badPingInMilliSec;
    
Methods Summary
public voidaddMetricToMap(int metric)


        int downIndex = convertBitsPerSec2meshIndex(lastDownloadBitsPerSec);
        int upIndex = convertBitsPerSec2meshIndex(lastUploadBitsPerSec);

        totalPointsInMap++;

        if( metric<goodPingInMilliSec ){
            gridRegion[upIndex][downIndex].incrementMetricCount( GridRegion.INDEX_PING_GOOD );
        }else if( metric<badPingInMilliSec ){
            gridRegion[upIndex][downIndex].incrementMetricCount( GridRegion.INDEX_PING_NEUTRAL );
        }else{
            gridRegion[upIndex][downIndex].incrementMetricCount( GridRegion.INDEX_PING_BAD );
        }

    
private com.aelitis.azureus.core.speedmanager.impl.v2.PingSpaceMapper$Result[]calculate()
Look at the Map and find the highest index for each catagory.

return
Result[2], where index 0 is goodPing, index 1 is anyPing


                                
      

        Result[] retVal = new Result[2];
        retVal[GOOD_PING_INDEX] = new Result();
        retVal[ANY_PING_INDEX] = new Result();

        for(int upIndex=0;upIndex<maxMeshIndex;upIndex++){
            for(int downIndex=0;downIndex<maxMeshIndex;downIndex++)
            {
                //Register this grid point if it has more good then bad pings.
                float rating = gridRegion[upIndex][downIndex].getRating();
                if( rating>0.0f ){
                    retVal[GOOD_PING_INDEX].checkAndUpdate(upIndex,downIndex);
                }

                //Register this grid point if it has any ping values.
                int count = gridRegion[upIndex][downIndex].getTotal();
                if( count>0 ){
                    retVal[ANY_PING_INDEX].checkAndUpdate(upIndex,downIndex);
                }

            }//for
        }//for

        return retVal;
    
private intconvertBitsPerSec2meshIndex(int bitsPerSec)
We have a hard coded mesh. 0-9999 = 0, 10000-

param
bitsPerSec -
return
- mesh index.


        if( bitsPerSec<0){
            return 0;
        }

        int bytesPerSec = bitsPerSec/1024;

        if( bytesPerSec<100){
            return bytesPerSec/10;
        }else if(bytesPerSec<500){
            return 10 + ((bytesPerSec-100)/50);
        }else if(bytesPerSec<5000){
            return 10 + 8 + ((bytesPerSec-500)/100);
        }

        //return max mesh index.
        return 10 + 8 + 45;
    
private intconvertMeshIndex2bitsPerSec(int meshIndex)
The reverse of bit/sec -> mesh index calculation.

param
meshIndex - value between 0 and 70
return
lowest BitsPerSecond that meets that criteria.


        int bytesPerSec=0;
        if(meshIndex<=0){
            return 0;
        }

        if(meshIndex<=10){
            bytesPerSec = meshIndex*10;
        }else if(meshIndex<=18){
            bytesPerSec = 100 + (meshIndex-10) * 50;
        }else{
            bytesPerSec = 500 + (meshIndex-18) * 100;
        }

        return bytesPerSec*1024;
    
private voidcreateNewGrid()

        //create the mesh. We will have 70 by 70 grid. Even though we only use 63.
        gridRegion = null;
        gridRegion = new GridRegion[maxMeshIndex][maxMeshIndex];
        for(int upIndex=0;upIndex<maxMeshIndex;upIndex++){
            for(int downIndex=0;downIndex<maxMeshIndex;downIndex++){
                gridRegion[upIndex][downIndex] = new GridRegion();
            }
        }
    
private com.aelitis.azureus.core.speedmanager.impl.v2.PingSpaceMapper$ResultgetHighestMeshIndexWithAnyPing()

        Result[] retVal = calculate();
        return retVal[ANY_PING_INDEX];
    
private com.aelitis.azureus.core.speedmanager.impl.v2.PingSpaceMapper$ResultgetHighestMeshIndexWithGoodPing()


      
       Result[] retVal = calculate();
       return retVal[GOOD_PING_INDEX];
    
public intguessDownloadLimit()
Make a guess at the download capacity based on metric data.

return
-


        Result result = getHighestMeshIndexWithGoodPing();
        int downMeshIndex = result.getDownloadIndex();
        return convertMeshIndex2bitsPerSec( downMeshIndex );
    
public intguessUploadLimit()
Make a guess at the upload capacity based on metric data.

return
-


        Result result = getHighestMeshIndexWithGoodPing();
        int upMeshIndex = result.getUploadIndex();
        return convertMeshIndex2bitsPerSec( upMeshIndex );
    
public booleanhadChockingPing(boolean isDownloadTest)
Try to determine if a chocking ping occured during this test.

param
isDownloadTest - set true if this is a download_search_test. set false if upload search test.
return
- true if it appears a chocking ping occured.


        Result[] res = calculate();

        int goodPingIndex;
        int highPingIndex;

        if( isDownloadTest ){
            goodPingIndex = res[GOOD_PING_INDEX].getDownloadIndex();
            highPingIndex = res[ANY_PING_INDEX].getDownloadIndex();
        }else{
            goodPingIndex = res[GOOD_PING_INDEX].getUploadIndex();
            highPingIndex = res[ANY_PING_INDEX].getUploadIndex();
        }

        return (highPingIndex>goodPingIndex);
    
public voidreset()
Start accumlating data from scratch.

        totalPointsInMap=0;
        createNewGrid();
    
public voidsetCurrentTransferRates(int downloadBitPerSec, int uploadBitsPerSec)

        lastDownloadBitsPerSec = downloadBitPerSec;
        lastUploadBitsPerSec = uploadBitsPerSec;