8
votes

Y a-t-il un code pour l'adresse et le masque de réseau Bitwise et IPv6 (préfixe)?

Je veux poser des questions sur le calcul du réseau IPv6 et du côté hôte.

Par exemple, j'ai l'adresse IPv6 2001: 470: 1f15: 1BCD: 34 :: 41 et préfixe 96 .

Connaissez-vous un moyen facile de faire un bit bitwise et entre l'adresse IPv6 et le préfixe?

selon IPv4: xxx

si simple.

Je veux faire la même chose à l'adresse IPv6. Mais l'adresse IPv6 est de 16 octets, vous ne pouvez donc pas utiliser non signé INT pour cela.

Y a-t-il une API à faire cela? Ou devrais-je utiliser des tableaux?


2 commentaires

Si vous écrivez 255.255.255.0 AS / 24 AS / 24, le bit tripdling est presque identique.


Notez que vous ne devriez pas utiliser non signé INT pour IPv4 non plus; Vous devriez utiliser uint32_t (ou un typef de celui-ci).


6 Réponses :


1
votes

Vous pouvez convertir l'adresse en binaire dans l'ordre d'octet de réseau avec inet_pton . Puis définissez / effacer les bits un octet à la fois.


0 commentaires

0
votes

Menace La IP aime une matrice de 16 octets, ignorez le masqué / 8 octets dans le prochain masque d'octet le plus élevé masqué% 8 BITS, définissez les autres sur < code> 0 xxx

a écrit le code ici, il n'a donc pas été testé mais je pense que vous pouvez utiliser quelque chose comme ça


0 commentaires

2
votes

Calculer le masque de préfixe Longueur:

bool
inet6_lnaof (
        struct in6_addr* restrict       dst,
        const struct in6_addr* restrict src,
        const struct in6_addr* restrict netmask
        )
{
        bool has_lna = FALSE;

        assert (NULL != dst);
        assert (NULL != src);
        assert (NULL != netmask);

        for (unsigned i = 0; i < 16; i++) {
                dst->s6_addr[i] = src->s6_addr[i] & netmask->s6_addr[i];
                has_lna |= (0 != (src->s6_addr[i] & !netmask->s6_addr[i]));
        }

        return has_lna;
}


2 commentaires

Alerte de corruption mémoire! Astuce: Combien de fois votre boucle est-elle itérale si la préfixe est, dise, 3?


@JDEBP testé en multiples de 8 seulement (TM) :-)



0
votes

gars j'ai résolu mon problème Le code source est ci-dessous l'utiliser et continuer à coder: D: AVERTISSEMENT La fonction suppose que l'adresse IPv6 est valide., Mon type est: xxx


1 commentaires

Wow, ainsi convolué avec une utilisation ambiguë du mot "masque".



2
votes

OK, je l'ai fait en C plutôt que C ++, mais cela devrait fonctionner. Aussi, il utilise bswap_64 code> qui est Afaik une extension GNU, donc peut ne pas fonctionner sur tout.

Il semble être très rapide sur AMD64 et plus vite que la solution actuelle Yasar a proposé: P>

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdint.h>

#include <arpa/inet.h>

#if defined __GNUC__ && __GNUC__ >= 2
#include <byteswap.h>
#else
#error "Sorry, you need GNU for this"
#endif

struct split
{
  uint64_t start;
  uint64_t end;
};

void ipv6_prefix (unsigned char *masked, unsigned char *packed, int prefix)
{
  struct split parts;
  uint64_t mask = 0;
  unsigned char *p = masked;

  memset(masked, 0, sizeof(struct in6_addr));
  memcpy(&parts, packed, sizeof(parts));

  if (prefix <= 64)
  {
    mask = bswap_64(bswap_64(parts.start) & ((uint64_t) (~0) << (64 - prefix)));
    memcpy(masked, &mask, sizeof(uint64_t));
    return;
  }

  prefix -= 64;

  memcpy(masked, &(parts.start), sizeof(uint64_t));
  p += sizeof(uint64_t);
  mask = bswap_64(bswap_64(parts.end) & (uint64_t) (~0) << (64 - prefix));
  memcpy(p, &mask, sizeof(uint64_t));
}

int main (int argc, char **argv)
{
  unsigned char packed[sizeof(struct in6_addr)];
  unsigned char masked[sizeof(struct in6_addr)];
  char buf[INET6_ADDRSTRLEN], *p;
  int prefix = 56;

  if (argc < 2)
    return 1;

  if ((p = strchr(argv[1], '/')))
  {
    *p++ = '\0';
    prefix = atoi(p);
  }

  inet_pton(AF_INET6, argv[1], packed);

  ipv6_prefix(masked, packed, prefix);

  inet_ntop(AF_INET6, masked, buf, INET6_ADDRSTRLEN);
  printf("prefix = %s/%d\n", buf, prefix);
  return 0;
}


1 commentaires

Je viens de l'essayer sur une carte virtuelle I686 et c'est nettement plus rapide que cela aussi.



0
votes

Voici une minuterie simple: xxx


0 commentaires