MainActivity.java 18 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627
  1. package de.tudarmstadt.informatik.hostage.ui;
  2. import java.util.ArrayList;
  3. import java.util.HashMap;
  4. import android.app.Activity;
  5. import android.app.ActivityManager;
  6. import android.app.ActivityManager.RunningServiceInfo;
  7. import android.content.BroadcastReceiver;
  8. import android.content.ComponentName;
  9. import android.content.Context;
  10. import android.content.Intent;
  11. import android.content.IntentFilter;
  12. import android.content.ServiceConnection;
  13. import android.content.SharedPreferences;
  14. import android.os.Bundle;
  15. import android.os.Handler;
  16. import android.os.IBinder;
  17. import android.support.v4.content.LocalBroadcastManager;
  18. import android.view.GestureDetector;
  19. import android.view.GestureDetector.SimpleOnGestureListener;
  20. import android.view.Menu;
  21. import android.view.MenuItem;
  22. import android.view.MotionEvent;
  23. import android.view.View;
  24. import android.view.View.OnTouchListener;
  25. import android.view.animation.Animation;
  26. import android.view.animation.AnimationUtils;
  27. import android.widget.AdapterView;
  28. import android.widget.AdapterView.OnItemClickListener;
  29. import android.widget.CheckBox;
  30. import android.widget.ImageView;
  31. import android.widget.ListView;
  32. import android.widget.TextView;
  33. import android.widget.ToggleButton;
  34. import android.widget.ViewAnimator;
  35. import de.tudarmstadt.informatik.hostage.HoneyService;
  36. import de.tudarmstadt.informatik.hostage.HoneyService.LocalBinder;
  37. import de.tudarmstadt.informatik.hostage.R;
  38. import de.tudarmstadt.informatik.hostage.commons.HelperUtils;
  39. import de.tudarmstadt.informatik.hostage.db.HostageDbHelper;
  40. import de.tudarmstadt.informatik.hostage.logging.LogResultReceiver;
  41. import de.tudarmstadt.informatik.hostage.logging.LogResultReceiver.Receiver;
  42. import de.tudarmstadt.informatik.hostage.logging.Logger;
  43. /**
  44. * MainActivity is the central activity for the GUI of the application.
  45. * MainActivity is launched when the application is first started. It shows the
  46. * user: <br>
  47. * - information about the network<br>
  48. * - light indicators for recorded attacks on each protocol<br>
  49. * - amount of attacks on each protocols<br>
  50. * The user can start and stop services.
  51. *
  52. * @author Mihai Plasoianu
  53. * @author Lars Pandikow
  54. * @author Wulf Pfeiffer
  55. */
  56. public class MainActivity extends Activity implements Receiver {
  57. /**
  58. * Integer representing a grey light.
  59. */
  60. public static final int LIGHT_GREY = 0x01;
  61. /**
  62. * Integer representing a green light.
  63. */
  64. public static final int LIGHT_GREEN = 0x02;
  65. /**
  66. * Integer representing a red light.
  67. */
  68. public static final int LIGHT_RED = 0x03;
  69. /**
  70. * Integer representing a yellow light.
  71. */
  72. public static final int LIGHT_YELLOW = 0x04;
  73. public LogResultReceiver logResultReceiver;
  74. private SharedPreferences connectionInfo;
  75. private HoneyService mService;
  76. private boolean serviceBound;
  77. // variables for the swipe animation
  78. private ViewAnimator viewAnimator;
  79. private GestureDetector gestureDetector;
  80. private Animation animFlipInLR;
  81. private Animation animFlipOutLR;
  82. private Animation animFlipInRL;
  83. private Animation animFlipOutRL;
  84. private ListView listView;
  85. private ListViewAdapter adapter;
  86. private boolean isBssidSeen = false;
  87. /**
  88. * Connection to bind the background service
  89. *
  90. * @see HoneyService
  91. */
  92. private ServiceConnection mConnection = new ServiceConnection() {
  93. /**
  94. * After the service is bound, check which has been clicked and start
  95. * it.
  96. *
  97. * @see android.content.ServiceConnection#onServiceConnected(android.content.ComponentName)
  98. */
  99. @Override
  100. public void onServiceConnected(ComponentName name, IBinder service) {
  101. mService = ((LocalBinder) service).getService();
  102. serviceBound = true;
  103. updateUI();
  104. }
  105. /**
  106. * After the service is unbound, delete reference.
  107. *
  108. * @see android.content.ServiceConnection#onServiceDisconnected(android.content.ComponentName)
  109. */
  110. @Override
  111. public void onServiceDisconnected(ComponentName name) {
  112. mService = null;
  113. serviceBound = false;
  114. }
  115. };
  116. /**
  117. * Receiver for custom broadcast.
  118. *
  119. * @see #BROADCAST
  120. */
  121. private BroadcastReceiver mReceiver = new BroadcastReceiver() {
  122. @Override
  123. public void onReceive(Context context, Intent intent) {
  124. // Update user interface.
  125. updateUI();
  126. updateConnectionInfText();
  127. }
  128. };
  129. SimpleOnGestureListener simpleOnGestureListener = new SimpleOnGestureListener() {
  130. @Override
  131. public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) {
  132. float sensitvity = 50;
  133. if ((e1.getX() - e2.getX()) > sensitvity) {
  134. swipeRightToLeft();
  135. } else if ((e2.getX() - e1.getX()) > sensitvity) {
  136. swipeLeftToRight();
  137. }
  138. return true;
  139. }
  140. };
  141. /**
  142. * Called when User presses on/off button.
  143. *
  144. * @param view
  145. */
  146. public void buttonOnOffClick(View view) {
  147. if (((ToggleButton) view).isChecked()) {
  148. if (isParanoid()) {
  149. String[] protocols = getResources().getStringArray(R.array.protocols);
  150. for (String protocol : protocols) {
  151. mService.startListener(protocol);
  152. }
  153. } else {
  154. if (mService.isRunning("SMB")) {
  155. mService.stopListener("SMB");
  156. } else {
  157. mService.startListener("SMB");
  158. }
  159. }
  160. } else {
  161. mService.stopListeners();
  162. stopAndUnbind();
  163. }
  164. }
  165. @Override
  166. public boolean onCreateOptionsMenu(Menu menu) {
  167. getMenuInflater().inflate(R.menu.main, menu);
  168. return true;
  169. }
  170. @Override
  171. public boolean onOptionsItemSelected(MenuItem item) {
  172. // Handle item selection
  173. switch (item.getItemId()) {
  174. case R.id.action_settings:
  175. startActivity(new Intent(this, SettingsActivity.class));
  176. break;
  177. case R.id.action_about:
  178. startActivity(new Intent(this, AboutActivity.class));
  179. break;
  180. default:
  181. }
  182. return super.onOptionsItemSelected(item);
  183. }
  184. @Override
  185. public void onReceiveResult(int resultCode, Bundle resultData) {
  186. isBssidSeen = resultData.getBoolean("result");
  187. }
  188. @Override
  189. public boolean onTouchEvent(MotionEvent event) {
  190. return gestureDetector.onTouchEvent(event);
  191. }
  192. /**
  193. * Starts the ViewLog activity, when the Button is pressed.
  194. *
  195. * @see ViewLog
  196. * @param view
  197. * View elements which triggers the method call.
  198. */
  199. public void showLog(View view) {
  200. startActivity(new Intent(this, ViewLog.class));
  201. }
  202. public void startPlayGround(View view) {
  203. startActivity(new Intent(this, PlayGroundActivity.class));
  204. }
  205. /**
  206. * Binds service to Activity
  207. *
  208. * @see HoneyService
  209. */
  210. private void bindService() {
  211. bindService(getServiceIntent(), mConnection, BIND_AUTO_CREATE);
  212. }
  213. /**
  214. * Returns an intent to start HoneyService.
  215. *
  216. * @return An Intent to start HoneyService
  217. */
  218. private Intent getServiceIntent() {
  219. return new Intent(this, HoneyService.class);
  220. }
  221. /**
  222. * Initializes the ListView. Creating its contents dynamic from protocol
  223. * res/values/protocols.xml
  224. */
  225. private void initListView() {
  226. ArrayList<HashMap<String, String>> data = new ArrayList<HashMap<String, String>>();
  227. for (String protocol : getResources().getStringArray(R.array.protocols)) {
  228. HashMap<String, String> d = new HashMap<String, String>();
  229. d.put("light", String.valueOf(R.drawable.light_grey));
  230. d.put("protocol", protocol);
  231. d.put("connections", "-");
  232. data.add(d);
  233. }
  234. listView = (ListView) findViewById(R.id.listViewProtocols);
  235. adapter = new ListViewAdapter(getLayoutInflater(), data);
  236. listView.setAdapter(adapter);
  237. listView.setOnTouchListener(new OnTouchListener() {
  238. @Override
  239. public boolean onTouch(View v, MotionEvent event) {
  240. return gestureDetector.onTouchEvent(event);
  241. }
  242. });
  243. listView.setOnItemClickListener(new OnItemClickListener() {
  244. @Override
  245. public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
  246. String protocolName = (String) ((HashMap<?, ?>) adapter.getItem(position)).get("protocol");
  247. if (mService.isRunning(protocolName)) {
  248. mService.stopListener(protocolName);
  249. } else {
  250. mService.startListener(protocolName);
  251. }
  252. }
  253. });
  254. }
  255. /**
  256. * Initializes variables for screen animation
  257. */
  258. private void initViewAnimator() {
  259. viewAnimator = (ViewAnimator) findViewById(R.id.viewAnimator);
  260. gestureDetector = new GestureDetector(this, simpleOnGestureListener);
  261. animFlipInLR = AnimationUtils.loadAnimation(this, R.anim.in_left_to_right);
  262. animFlipOutLR = AnimationUtils.loadAnimation(this, R.anim.out_left_to_right);
  263. animFlipInRL = AnimationUtils.loadAnimation(this, R.anim.in_right_to_left);
  264. animFlipOutRL = AnimationUtils.loadAnimation(this, R.anim.out_right_to_left);
  265. }
  266. /**
  267. * Checks if user selected paranoid mode.
  268. *
  269. * @return True when paranoid mode is selected, else returns false.
  270. */
  271. private boolean isParanoid() {
  272. return ((CheckBox) findViewById(R.id.checkBoxParanoid)).isChecked();
  273. }
  274. /**
  275. * Checks if a {@link HoneyService} instance is running.
  276. *
  277. * @return True if {@link HoneyService} is running, else false.
  278. */
  279. private boolean isServiceBound() {
  280. return serviceBound;
  281. }
  282. /**
  283. * Checks if a {@link HoneyService} instance is running.
  284. *
  285. * @return True if {@link HoneyService} is running, else false.
  286. */
  287. private boolean isServiceRunning() {
  288. ActivityManager manager = (ActivityManager) getSystemService(Context.ACTIVITY_SERVICE);
  289. for (RunningServiceInfo service : manager.getRunningServices(Integer.MAX_VALUE)) {
  290. if (service.service.getClassName().equals(HoneyService.class.getName())) {
  291. return true;
  292. }
  293. }
  294. return false;
  295. }
  296. /**
  297. * Register broadcast receiver for custom broadcast.
  298. *
  299. * @see #BROADCAST
  300. */
  301. private void registerReceiver() {
  302. LocalBroadcastManager.getInstance(this).registerReceiver(mReceiver, new IntentFilter(getString(R.string.broadcast)));
  303. }
  304. /**
  305. * If mobile phone is connected to a wireless network starts the background
  306. * service ands binds itself to it. Else notifies the user that service
  307. * could not be started.
  308. */
  309. private void startAndBind() {
  310. startService(getServiceIntent());
  311. bindService();
  312. }
  313. /**
  314. * Stops service and unbinds it.
  315. *
  316. * @see HoneyService
  317. */
  318. private void stopAndUnbind() {
  319. unbindService();
  320. stopService(getServiceIntent());
  321. }
  322. /**
  323. * Called when a swipe to the Right is registered.
  324. */
  325. private void swipeLeftToRight() {
  326. if (viewAnimator.getDisplayedChild() == 1) {
  327. viewAnimator.setInAnimation(animFlipInLR);
  328. viewAnimator.setOutAnimation(animFlipOutLR);
  329. viewAnimator.setDisplayedChild(0);
  330. }
  331. }
  332. /**
  333. * Called when a swipe to the Left is registered.
  334. */
  335. private void swipeRightToLeft() {
  336. if (viewAnimator.getDisplayedChild() == 0) {
  337. viewAnimator.setInAnimation(animFlipInRL);
  338. viewAnimator.setOutAnimation(animFlipOutRL);
  339. viewAnimator.setDisplayedChild(1);
  340. }
  341. }
  342. /**
  343. * Unbinds service.
  344. *
  345. * @see HoneyService
  346. */
  347. private void unbindService() {
  348. unbindService(mConnection);
  349. }
  350. /**
  351. * Unregisters broadcast receiver for custom broadcast.
  352. *
  353. * @see #BROADCAST
  354. */
  355. private void unregisterReceiver() {
  356. LocalBroadcastManager.getInstance(this).unregisterReceiver(mReceiver);
  357. }
  358. /**
  359. * Gets Information about connection state and updates the GUI.
  360. */
  361. private void updateConnectionInfText() {
  362. TextView ssidView = (TextView) findViewById(R.id.textViewSSIDValue);
  363. TextView bssidView = (TextView) findViewById(R.id.textViewBSSIDValue);
  364. TextView internalIPView = (TextView) findViewById(R.id.textViewInternalIPValue);
  365. TextView externalIPView = (TextView) findViewById(R.id.textViewExternalIPValue);
  366. // externalIPView.setText("Loading...");
  367. // Get connection information
  368. String ssid = connectionInfo.getString(getString(R.string.connection_info_ssid), null);
  369. String bssid = connectionInfo.getString(getString(R.string.connection_info_bssid), null);
  370. String internalIP = connectionInfo.getString(getString(R.string.connection_info_internal_ip), null);
  371. String externalIP = connectionInfo.getString(getString(R.string.connection_info_external_ip), null);
  372. // Set text fields
  373. if (ssid != null)
  374. ssidView.setText(ssid);
  375. else
  376. ssidView.setText("-");
  377. if (bssid != null)
  378. bssidView.setText(bssid);
  379. else
  380. bssidView.setText("-");
  381. if (internalIP != null)
  382. internalIPView.setText(internalIP);
  383. else
  384. internalIPView.setText("-");
  385. if (externalIP != null)
  386. externalIPView.setText(externalIP);
  387. else
  388. externalIPView.setText("-");
  389. }
  390. /**
  391. * Sets the connections count for a given protocol.
  392. *
  393. * @param connections
  394. * New value for recorded connections.
  395. * @param protocolName
  396. * Name of the protocol which should be updated.
  397. */
  398. private void updateProtocolConnections(int connections, String protocolName) {
  399. for (int i = 0; i < adapter.getCount(); ++i) {
  400. HashMap<String, String> d = ((HashMap<String, String>) adapter.getItem(i));
  401. if (d.get("protocol").equals(protocolName)) {
  402. d.put("connections", String.valueOf(connections));
  403. }
  404. }
  405. adapter.notifyDataSetChanged();
  406. }
  407. /**
  408. * Sets the light indicator for a given protocol.
  409. *
  410. * @param light
  411. * Integer code to set the light color.
  412. * @param protocolName
  413. * Name of the protocol which should be updated.
  414. */
  415. private void updateProtocolLight(int light, String protocolName) {
  416. for (int i = 0; i < adapter.getCount(); ++i) {
  417. HashMap<String, String> d = (HashMap<String, String>) adapter.getItem(i);
  418. if (d.get("protocol").equals(protocolName)) {
  419. switch (light) {
  420. case LIGHT_GREY:
  421. d.put("light", String.valueOf(R.drawable.light_grey));
  422. d.put("connections", "-");
  423. break;
  424. case LIGHT_GREEN:
  425. d.put("light", String.valueOf(R.drawable.light_green));
  426. break;
  427. case LIGHT_RED:
  428. d.put("light", String.valueOf(R.drawable.light_red));
  429. break;
  430. case LIGHT_YELLOW:
  431. d.put("light", String.valueOf(R.drawable.light_yellow));
  432. break;
  433. }
  434. }
  435. }
  436. adapter.notifyDataSetChanged();
  437. }
  438. /**
  439. * Sets the big light indicator.
  440. *
  441. * @param light
  442. * Integer code to set the light color.
  443. * @see #LIGHT_GREY
  444. * @see #LIGHT_GREEN
  445. * @see #LIGHT_RED
  446. * @see #LIGHT_YELLOW
  447. */
  448. private void updateStatusLight(int light) {
  449. switch (light) {
  450. case LIGHT_GREY:
  451. ((ImageView) findViewById(R.id.imageViewLight)).setImageResource(R.drawable.light_grey_large);
  452. break;
  453. case LIGHT_GREEN:
  454. ((ImageView) findViewById(R.id.imageViewLight)).setImageResource(R.drawable.light_green_large);
  455. break;
  456. case LIGHT_RED:
  457. ((ImageView) findViewById(R.id.imageViewLight)).setImageResource(R.drawable.light_red_large);
  458. break;
  459. case LIGHT_YELLOW:
  460. ((ImageView) findViewById(R.id.imageViewLight)).setImageResource(R.drawable.light_yellow_large);
  461. break;
  462. }
  463. }
  464. /* ############# Help functions for animation ################## */
  465. /**
  466. * Updates Information shown by the GUI.
  467. */
  468. private void updateUI() {
  469. boolean activeListeners = false;
  470. boolean activeHandlers = false;
  471. boolean yellowLight = false;
  472. // Check for all protocols if listeners are active and attacks have been
  473. // recorded
  474. // Update protocol lights and connection information.
  475. for (String protocol : getResources().getStringArray(R.array.protocols)) {
  476. if (isServiceBound()) {
  477. // Check if protocol is active
  478. if (mService.isRunning(protocol)) {
  479. activeListeners = true;
  480. int handlerCount = mService.getNumberOfActiveConnections(protocol);
  481. // Check if attacks have been recorded in this session.
  482. if (handlerCount > 0) {
  483. activeHandlers = true;
  484. updateProtocolLight(LIGHT_RED, protocol);
  485. updateProtocolConnections(handlerCount, protocol);
  486. } else {
  487. // Check if the bssid of the wireless network has
  488. // already
  489. // been recorded as infected.
  490. Logger.isBssidSeen(getApplicationContext(), protocol, HelperUtils.getBSSID(getApplicationContext()), logResultReceiver);
  491. HostageDbHelper dbh = new HostageDbHelper(this);
  492. if (dbh.bssidSeen(protocol, connectionInfo.getString(getString(R.string.connection_info_bssid), null))) {
  493. updateProtocolLight(LIGHT_YELLOW, protocol);
  494. yellowLight = true;
  495. } else {
  496. updateProtocolLight(LIGHT_GREEN, protocol);
  497. }
  498. updateProtocolConnections(0, protocol);
  499. }
  500. } else {
  501. updateProtocolLight(LIGHT_GREY, protocol);
  502. }
  503. } else {
  504. updateProtocolLight(LIGHT_GREY, protocol);
  505. }
  506. }
  507. // Update the big attack indicator.
  508. if (activeListeners) {
  509. if (activeHandlers) {
  510. updateStatusLight(LIGHT_RED);
  511. } else {
  512. if (yellowLight) {
  513. updateStatusLight(LIGHT_YELLOW);
  514. } else {
  515. updateStatusLight(LIGHT_GREEN);
  516. }
  517. }
  518. ((ToggleButton) findViewById(R.id.toggleButtonOnOff)).setChecked(true);
  519. findViewById(R.id.checkBoxParanoid).setEnabled(false);
  520. } else {
  521. updateStatusLight(LIGHT_GREY);
  522. ((ToggleButton) findViewById(R.id.toggleButtonOnOff)).setChecked(false);
  523. findViewById(R.id.checkBoxParanoid).setEnabled(true);
  524. }
  525. }
  526. @Override
  527. protected void onCreate(Bundle savedInstanceState) {
  528. super.onCreate(savedInstanceState);
  529. logResultReceiver = new LogResultReceiver(new Handler());
  530. setContentView(R.layout.activity_main);
  531. connectionInfo = getSharedPreferences(getString(R.string.connection_info), Context.MODE_PRIVATE);
  532. // Create dynamic view elements
  533. initViewAnimator();
  534. initListView();
  535. // Initialize Class variables
  536. startAndBind();
  537. }
  538. @Override
  539. protected void onDestroy() {
  540. // Unbind running service
  541. if (!mService.hasRunningListeners()) {
  542. stopAndUnbind();
  543. }
  544. super.onDestroy();
  545. }
  546. @Override
  547. protected void onStart() {
  548. super.onStart();
  549. // Register Broadcast Receiver
  550. registerReceiver();
  551. logResultReceiver.setReceiver(this);
  552. // Bind service if running, else check for connection change and delete
  553. // sessionData
  554. if (isServiceRunning()) {
  555. bindService(getServiceIntent(), mConnection, BIND_AUTO_CREATE);
  556. }
  557. // Update UI
  558. updateConnectionInfText();
  559. }
  560. @Override
  561. protected void onStop() {
  562. // Unregister Broadcast Receiver
  563. unregisterReceiver();
  564. logResultReceiver.setReceiver(null);
  565. super.onStop();
  566. }
  567. }