it-swarm.dev

Obtendo o endereço MAC no Android 6.0

Estou desenvolvendo um aplicativo que obtém o endereço MAC do dispositivo, mas desde o Android 6.0 meu código não funciona, me dando um valor incorreto.

Aqui está meu código ...

    public String ObtenMAC()
{
    WifiManager manager = (WifiManager) getSystemService(Context.WIFI_SERVICE);
    WifiInfo info = manager.getConnectionInfo();

    return(info.getMacAddress().toUpperCase());
}

Em vez do endereço MAC real, ele retorna um código estranho: "02: 00: 00: 00: 00: 00".

Alguém pode me ajudar a resolver isso?.

41
Mazinger

Por favor, consulte Alterações do Android 6.0

Para fornecer aos usuários maior proteção de dados, a partir desta versão, o Android remove o acesso programático ao identificador de hardware local do dispositivo para aplicativos que usam as APIs de Wi-Fi e Bluetooth. Os métodos WifiInfo.getMacAddress () e BluetoothAdapter.getAddress () agora retornam um valor constante de 02: 00: 00: 00: 00: 00.

Para acessar os identificadores de hardware de dispositivos externos próximos por meio de varreduras Bluetooth e Wi-Fi, seu aplicativo deve agora ter as permissões ACCESS_FINE_LOCATION ou ACCESS_COARSE_LOCATION.

33
Siu

Use abaixo o código para obter o endereço Mac no Android 6.0

public static String getMacAddr() {
    try {
        List<NetworkInterface> all = Collections.list(NetworkInterface.getNetworkInterfaces());
        for (NetworkInterface nif : all) {
            if (!nif.getName().equalsIgnoreCase("wlan0")) continue;

            byte[] macBytes = nif.getHardwareAddress();
            if (macBytes == null) {
                return "";
            }

            StringBuilder res1 = new StringBuilder();
            for (byte b : macBytes) {
                res1.append(Integer.toHexString(b & 0xFF) + ":");
            }

            if (res1.length() > 0) {
                res1.deleteCharAt(res1.length() - 1);
            }
            return res1.toString();
        }
    } catch (Exception ex) {
        //handle exception
    }
    return "";
}
26
Chintan Rathod

Eu não recebi a resposta acima para o trabalho, mas tropecei em outra resposta.

Aqui está um método completo e simples para obter o endereço IPv6 e depois obter o endereço MAC dele.

Como obter o endereço MAC Wi-Fi no Android Marshmallow

public static String getMacAddr() {
    try {
        List<NetworkInterface> all = Collections.list(NetworkInterface.getNetworkInterfaces());
        for (NetworkInterface nif : all) {
            if (!nif.getName().equalsIgnoreCase("wlan0")) continue;

            byte[] macBytes = nif.getHardwareAddress();
            if (macBytes == null) {
                return "";
            }

            StringBuilder res1 = new StringBuilder();
            for (byte b : macBytes) {
                res1.append(String.format("%02X:",b));
            }

            if (res1.length() > 0) {
                res1.deleteCharAt(res1.length() - 1);
            }
            return res1.toString();
        }
    } catch (Exception ex) {
    }
    return "02:00:00:00:00:00";
}

Testado já e funciona. Muito obrigado a Rob Anderson!

13
ADDER

este é o código completo de 2 maneiras de obtê-lo com sucesso no Marshmallow, basta copiar e isso vai funcionar! 

//Android 6.0 : Access to mac address from WifiManager forbidden
    private static final String marshmallowMacAddress = "02:00:00:00:00:00";
    private static final String fileAddressMac = "/sys/class/net/wlan0/address";    

public static String recupAdresseMAC(WifiManager wifiMan) {
        WifiInfo wifiInf = wifiMan.getConnectionInfo();

        if(wifiInf.getMacAddress().equals(marshmallowMacAddress)){
            String ret = null;
            try {
                ret= getAdressMacByInterface();
                if (ret != null){
                    return ret;
                } else {
                    ret = getAddressMacByFile(wifiMan);
                    return ret;
                }
            } catch (IOException e) {
                Log.e("MobileAccess", "Erreur lecture propriete Adresse MAC");
            } catch (Exception e) {
                Log.e("MobileAcces", "Erreur lecture propriete Adresse MAC ");
            }
        } else{
            return wifiInf.getMacAddress();
        }
        return marshmallowMacAddress;
    }

private static String getAdressMacByInterface(){
        try {
            List<NetworkInterface> all = Collections.list(NetworkInterface.getNetworkInterfaces());
            for (NetworkInterface nif : all) {
                if (nif.getName().equalsIgnoreCase("wlan0")) {
                    byte[] macBytes = nif.getHardwareAddress();
                    if (macBytes == null) {
                        return "";
                    }

                    StringBuilder res1 = new StringBuilder();
                    for (byte b : macBytes) {
                        res1.append(String.format("%02X:",b));
                    }

                    if (res1.length() > 0) {
                        res1.deleteCharAt(res1.length() - 1);
                    }
                    return res1.toString();
                }
            }

        } catch (Exception e) {
            Log.e("MobileAcces", "Erreur lecture propriete Adresse MAC ");
        }
        return null;
    }

private static String getAddressMacByFile(WifiManager wifiMan) throws Exception {
        String ret;
        int wifiState = wifiMan.getWifiState();

        wifiMan.setWifiEnabled(true);
        File fl = new File(fileAddressMac);
        FileInputStream fin = new FileInputStream(fl);
        StringBuilder builder = new StringBuilder();
    int ch;
    while((ch = fin.read()) != -1){
        builder.append((char)ch);
    }

    ret = builder.toString();
    fin.close();

        boolean enabled = WifiManager.WIFI_STATE_ENABLED == wifiState;
        wifiMan.setWifiEnabled(enabled);
        return ret;
    }

manifesto:

<uses-permission Android:name="Android.permission.ACCESS_WIFI_STATE" />
    <uses-permission Android:name="Android.permission.CHANGE_WIFI_STATE" />
  • Resumo: este código tentará obter o endereço MAC primeiro pela Interface e, se falhar, obtém-o pelo sistema de arquivos.

  • Nota: para o caminho do sistema de arquivos, você precisa ativar o Wi-Fi para acessar o arquivo.

thnx para a resposta de Sam aqui https://stackoverflow.com/a/39288868/3818437

9
mhdjazmati

Você pode obter o endereço MAC do endereço local do IPv6. Por exemplo, o endereço IPv6 "fe80 :: 1034: 56ff: fe78: 9abc" corresponde ao endereço MAC "12-34-56-78-9a-bc". Veja o código abaixo. Obtendo o endereço IPv6 WiFi requer apenas Android.permission.INTERNET.

Veja a página da Wikipedia Endereço IPv6 , particularmente a nota sobre "endereços locais" fe80 ::/64 e a seção "Modificado EUI-64".

/**
 * Gets an EUI-48 MAC address from an IPv6 link-local address.
 * E.g., the IPv6 address "fe80::1034:56ff:fe78:9abc"
 * corresponds to the MAC address "12-34-56-78-9a-bc".
 * <p/>
 * See the note about "local addresses" fe80::/64 and the section about "Modified EUI-64" in
 * the Wikipedia article "IPv6 address" at https://en.wikipedia.org/wiki/IPv6_address
 *
 * @param ipv6 An Inet6Address object.
 * @return The EUI-48 MAC address as a byte array, null on error.
 */
private static byte[] getMacAddressFromIpv6(final Inet6Address ipv6)
{
    byte[] eui48mac = null;

    if (ipv6 != null) {
        /*
         * Make sure that this is an fe80::/64 link-local address.
         */
        final byte[] ipv6Bytes = ipv6.getAddress();
        if ((ipv6Bytes != null) &&
                (ipv6Bytes.length == 16) &&
                (ipv6Bytes[0] == (byte) 0xfe) &&
                (ipv6Bytes[1] == (byte) 0x80) &&
                (ipv6Bytes[11] == (byte) 0xff) &&
                (ipv6Bytes[12] == (byte) 0xfe)) {
            /*
             * Allocate a byte array for storing the EUI-48 MAC address, then fill it
             * from the appropriate bytes of the IPv6 address. Invert the 7th bit
             * of the first byte and discard the "ff:fe" portion of the modified
             * EUI-64 MAC address.
             */
            eui48mac = new byte[6];
            eui48mac[0] = (byte) (ipv6Bytes[8] ^ 0x2);
            eui48mac[1] = ipv6Bytes[9];
            eui48mac[2] = ipv6Bytes[10];
            eui48mac[3] = ipv6Bytes[13];
            eui48mac[4] = ipv6Bytes[14];
            eui48mac[5] = ipv6Bytes[15];
        }
    }

    return eui48mac;
}
6
Yojimbo

Eu tento obter o endereço MAC com 2 métodos, primeiro pela interface e se a sua falha, eu entendo por sistema de arquivos, mas você precisa habilitar wifi para acessar o arquivo.

//Android 6.0 : Access to mac address from WifiManager forbidden
    private static final String marshmallowMacAddress = "02:00:00:00:00:00";
    private static final String fileAddressMac = "/sys/class/net/wlan0/address";    

public static String recupAdresseMAC(WifiManager wifiMan) {
        WifiInfo wifiInf = wifiMan.getConnectionInfo();

        if(wifiInf.getMacAddress().equals(marshmallowMacAddress)){
            String ret = null;
            try {
                ret= getAdressMacByInterface();
                if (ret != null){
                    return ret;
                } else {
                    ret = getAddressMacByFile(wifiMan);
                    return ret;
                }
            } catch (IOException e) {
                Log.e("MobileAccess", "Erreur lecture propriete Adresse MAC");
            } catch (Exception e) {
                Log.e("MobileAcces", "Erreur lecture propriete Adresse MAC ");
            }
        } else{
            return wifiInf.getMacAddress();
        }
        return marshmallowMacAddress;
    }

private static String getAdressMacByInterface(){
        try {
            List<NetworkInterface> all = Collections.list(NetworkInterface.getNetworkInterfaces());
            for (NetworkInterface nif : all) {
                if (nif.getName().equalsIgnoreCase("wlan0")) {
                    byte[] macBytes = nif.getHardwareAddress();
                    if (macBytes == null) {
                        return "";
                    }

                    StringBuilder res1 = new StringBuilder();
                    for (byte b : macBytes) {
                        res1.append(String.format("%02X:",b));
                    }

                    if (res1.length() > 0) {
                        res1.deleteCharAt(res1.length() - 1);
                    }
                    return res1.toString();
                }
            }

        } catch (Exception e) {
            Log.e("MobileAcces", "Erreur lecture propriete Adresse MAC ");
        }
        return null;
    }

private static String getAddressMacByFile(WifiManager wifiMan) throws Exception {
        String ret;
        int wifiState = wifiMan.getWifiState();

        wifiMan.setWifiEnabled(true);
        File fl = new File(fileAddressMac);
        FileInputStream fin = new FileInputStream(fl);
        ret = convertStreamToString(fin);
        fin.close();

        boolean enabled = WifiManager.WIFI_STATE_ENABLED == wifiState;
        wifiMan.setWifiEnabled(enabled);
        return ret;
    }

Adicione esta linha ao seu manifesto.

<uses-permission Android:name="Android.permission.ACCESS_WIFI_STATE" />
    <uses-permission Android:name="Android.permission.CHANGE_WIFI_STATE" />

Eu recomendo que você mantenha seu endereço MAC nas suas preferências como aqui 

mac = activity.getSharedPreferences("MAC_ADDRESS", Context.MODE_PRIVATE).getString("MAC_ADDRESS", "");
                if(mac == null || mac.equals("")){
                    WifiManager wifiMan = (WifiManager) activity.getSystemService(Context.WIFI_SERVICE);
                    mac = MobileAccess.recupAdresseMAC(wifiMan);
                    if(mac != null && !mac.equals("")){
                        SharedPreferences.Editor editor = activity.getSharedPreferences("MAC_ADDRESS", Context.MODE_PRIVATE).edit();
                        editor.putString("MAC_ADDRESS", mac).commit();
                    }
                }
4
Sam

As respostas estão corretas, mas cuidado, há uma mudança no Android 7. Você precisará usar o 

DevicePolicyManager e o método getWifiMacAddress. Os documentos oficiais têm um erro de digitação, o que significa que você não deve copiar/colar de lá.

DevicePolicyManager.getWifiMacAddress()

Refs: https://developer.Android.com/about/versions/nougat/Android-7.0-changes.html

Obter endereço do dispositivo Mac no Android Nougat e O programaticamente

1
Emanuel S

Primeiro você precisa adicionar permissão de usuário da Internet.

<uses-permission Android:name="Android.permission.INTERNET" />

Então você pode encontrar o mac sobre a API NetworkInterfaces.

public static String getMacAddr() {
    try {
        List<NetworkInterface> all = Collections.list(NetworkInterface.getNetworkInterfaces());
        for (NetworkInterface nif : all) {
            if (!nif.getName().equalsIgnoreCase("wlan0")) continue;

            byte[] macBytes = nif.getHardwareAddress();
            if (macBytes == null) {
                return "";
            }

            StringBuilder res1 = new StringBuilder();
            for (byte b : macBytes) {
                res1.append(String.format("%02X:",b));
            }

            if (res1.length() > 0) {
                res1.deleteCharAt(res1.length() - 1);
            }
            return res1.toString();
        }
    } catch (Exception ex) {
    }
    return "02:00:00:00:00:00";
}
1
Parveen Prajapati

É perfeitamente fino

package com.keshav.fetchmacaddress;

import Android.support.v7.app.AppCompatActivity;
import Android.os.Bundle;
import Android.util.Log;

import Java.net.InetAddress;
import Java.net.NetworkInterface;
import Java.net.SocketException;
import Java.net.UnknownHostException;
import Java.util.Collections;
import Java.util.List;

public class MainActivity extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        Log.e("keshav","getMacAddr -> " +getMacAddr());
    }

    public static String getMacAddr() {
        try {
            List<NetworkInterface> all = Collections.list(NetworkInterface.getNetworkInterfaces());
            for (NetworkInterface nif : all) {
                if (!nif.getName().equalsIgnoreCase("wlan0")) continue;

                byte[] macBytes = nif.getHardwareAddress();
                if (macBytes == null) {
                    return "";
                }

                StringBuilder res1 = new StringBuilder();
                for (byte b : macBytes) {
                    res1.append(Integer.toHexString(b & 0xFF) + ":");
                }

                if (res1.length() > 0) {
                    res1.deleteCharAt(res1.length() - 1);
                }
                return res1.toString();
            }
        } catch (Exception ex) {
            //handle exception
        }
        return "";
    }
}
0
Keshav Gera