Passed
Pull Request — master (#5733)
by David
08:44
created

follow_links()   A

Complexity

Conditions 3
Paths 3

Size

Total Lines 11
Code Lines 8

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 1
Metric Value
cc 3
eloc 8
c 1
b 0
f 1
nc 3
nop 1
dl 0
loc 11
rs 10
1
<?php
2
3
// identify possible botnet accounts:
4
// those with > MAX_HOSTS hosts
5
//
6
// could:
7
//      add other criteria like # of countries (based on IP addr)
8
//      consider only hosts with recent last RPC time
9
10
define ('MAX_HOSTS', 100);
11
12
require_once('../inc/boinc_db.inc');
13
14
// when hosts are merged, userid is set to zero
15
// and the rpc_seqno field is used to link to the non-zombie host.
16
// Follow links and return the latter.
17
//
18
function follow_links($id) {
19
    $orig_id = $id;
20
    $host = BoincHost::lookup_id($id);
21
    while ($host->userid == 0) {
22
        $host = BoincHost::lookup_id($host->rpc_seqno);
23
        if (!$host) {
24
            echo "(broken link in chain from host $orig_id)\n";
25
            return null;
26
        }
27
    }
28
    return $host;
29
}
30
31
function main() {
32
    $hosts = BoincHost::enum_fields('id, userid, last_ip_addr', '');
33
    $users = [];
34
    foreach ($hosts as $host) {
35
        if ($host->userid == 0) {
36
            $host = follow_links($host->id);
37
            if (!$host) continue;
38
        }
39
        if (array_key_exists($host->userid, $users)) {
40
            $users[$host->userid]++;
41
        } else {
42
            $users[$host->userid] = 1;
43
        }
44
    }
45
46
    foreach ($users as $id => $nhosts) {
47
        if ($nhosts < MAX_HOSTS) continue;
48
        $user = BoincUser::lookup_id($id);
49
        if ($user) {
50
            echo "$user->name has $nhosts hosts\n";
51
        } else {
52
            echo "unknown user $id has $nhosts hosts\n";
53
        }
54
    }
55
}
56
57
main();
58
59
?>
60