Quellcodebibliothek Statistik Leitseite products/Sources/formale Sprachen/C/Linux/drivers/net/wireless/ath/ath9k/   (Linux Kernel Version 6.17.9©)  Datei vom 24.10.2025 mit Größe 14 kB image not shown  

Quelle  peer_object.c   Sprache: C

 

// SPDX-License-Identifier: GPL-2.0-or-later
/* RxRPC remote transport endpoint record management
 *
 * Copyright (C) 2007, 2016 Red Hat, Inc. All Rights Reserved.
 * Written by David Howells (dhowells@redhat.com)
 */


#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt

#include <linux/module.h>
#include <linux/net.h>
#include <linux/skbuff.h>
#include <linux/udp.h>
#include <linux/in.h>
#include <linux/in6.h>
#include <linux/slab.h>
#include <linux/hashtable.h>
#include <net/sock.h>
#include <net/af_rxrpc.h>
#include <net/ip.h>
#include <net/route.h>
#include <net/ip6_route.h>
#include "ar-internal.h"

static const struct sockaddr_rxrpc rxrpc_null_addr;

/*
 * Hash a peer key.
 */

static unsigned long rxrpc_peer_hash_key(struct rxrpc_local *local,
      const struct sockaddr_rxrpc *srx)
{
 const u16 *p;
 unsigned int i, size;
 unsigned long hash_key;

 _enter("");

 hash_key = (unsigned long)local / __alignof__(*local);
 hash_key += srx->transport_type;
 hash_key += srx->transport_len;
 hash_key += srx->transport.family;

 switch (srx->transport.family) {
 case AF_INET:
  hash_key += (u16 __force)srx->transport.sin.sin_port;
  size = sizeof(srx->transport.sin.sin_addr);
  p = (u16 *)&srx->transport.sin.sin_addr;
  break;
#ifdef CONFIG_AF_RXRPC_IPV6
 case AF_INET6:
  hash_key += (u16 __force)srx->transport.sin.sin_port;
  size = sizeof(srx->transport.sin6.sin6_addr);
  p = (u16 *)&srx->transport.sin6.sin6_addr;
  break;
#endif
 default:
  WARN(1, "AF_RXRPC: Unsupported transport address family\n");
  return 0;
 }

 /* Step through the peer address in 16-bit portions for speed */
 for (i = 0; i < size; i += sizeof(*p), p++)
  hash_key += *p;

 _leave(" 0x%lx", hash_key);
 return hash_key;
}

/*
 * Compare a peer to a key.  Return -ve, 0 or +ve to indicate less than, same
 * or greater than.
 *
 * Unfortunately, the primitives in linux/hashtable.h don't allow for sorted
 * buckets and mid-bucket insertion, so we don't make full use of this
 * information at this point.
 */

static long rxrpc_peer_cmp_key(const struct rxrpc_peer *peer,
          struct rxrpc_local *local,
          const struct sockaddr_rxrpc *srx,
          unsigned long hash_key)
{
 long diff;

 diff = ((peer->hash_key - hash_key) ?:
  ((unsigned long)peer->local - (unsigned long)local) ?:
  (peer->srx.transport_type - srx->transport_type) ?:
  (peer->srx.transport_len - srx->transport_len) ?:
  (peer->srx.transport.family - srx->transport.family));
 if (diff != 0)
  return diff;

 switch (srx->transport.family) {
 case AF_INET:
  return ((u16 __force)peer->srx.transport.sin.sin_port -
   (u16 __force)srx->transport.sin.sin_port) ?:
   memcmp(&peer->srx.transport.sin.sin_addr,
          &srx->transport.sin.sin_addr,
          sizeof(struct in_addr));
#ifdef CONFIG_AF_RXRPC_IPV6
 case AF_INET6:
  return ((u16 __force)peer->srx.transport.sin6.sin6_port -
   (u16 __force)srx->transport.sin6.sin6_port) ?:
   memcmp(&peer->srx.transport.sin6.sin6_addr,
          &srx->transport.sin6.sin6_addr,
          sizeof(struct in6_addr));
#endif
 default:
  BUG();
 }
}

/*
 * Look up a remote transport endpoint for the specified address using RCU.
 */

static struct rxrpc_peer *__rxrpc_lookup_peer_rcu(
 struct rxrpc_local *local,
 const struct sockaddr_rxrpc *srx,
 unsigned long hash_key)
{
 struct rxrpc_peer *peer;
 struct rxrpc_net *rxnet = local->rxnet;

 hash_for_each_possible_rcu(rxnet->peer_hash, peer, hash_link, hash_key) {
  if (rxrpc_peer_cmp_key(peer, local, srx, hash_key) == 0 &&
      refcount_read(&peer->ref) > 0)
   return peer;
 }

 return NULL;
}

/*
 * Look up a remote transport endpoint for the specified address using RCU.
 */

struct rxrpc_peer *rxrpc_lookup_peer_rcu(struct rxrpc_local *local,
      const struct sockaddr_rxrpc *srx)
{
 struct rxrpc_peer *peer;
 unsigned long hash_key = rxrpc_peer_hash_key(local, srx);

 peer = __rxrpc_lookup_peer_rcu(local, srx, hash_key);
 if (peer)
  _leave(" = %p {u=%d}", peer, refcount_read(&peer->ref));
 return peer;
}

/*
 * assess the MTU size for the network interface through which this peer is
 * reached
 */

void rxrpc_assess_MTU_size(struct rxrpc_local *local, struct rxrpc_peer *peer)
{
 struct net *net = local->net;
 struct dst_entry *dst;
 struct rtable *rt;
 struct flowi fl;
 struct flowi4 *fl4 = &fl.u.ip4;
#ifdef CONFIG_AF_RXRPC_IPV6
 struct flowi6 *fl6 = &fl.u.ip6;
#endif

 peer->if_mtu = 1500;
 if (peer->max_data < peer->if_mtu - peer->hdrsize) {
  trace_rxrpc_pmtud_reduce(peer, 0, peer->if_mtu - peer->hdrsize,
      rxrpc_pmtud_reduce_route);
  peer->max_data = peer->if_mtu - peer->hdrsize;
 }

 memset(&fl, 0, sizeof(fl));
 switch (peer->srx.transport.family) {
 case AF_INET:
  rt = ip_route_output_ports(
   net, fl4, NULL,
   peer->srx.transport.sin.sin_addr.s_addr, 0,
   htons(7000), htons(7001), IPPROTO_UDP, 0, 0);
  if (IS_ERR(rt)) {
   _leave(" [route err %ld]", PTR_ERR(rt));
   return;
  }
  dst = &rt->dst;
  break;

#ifdef CONFIG_AF_RXRPC_IPV6
 case AF_INET6:
  fl6->flowi6_iif = LOOPBACK_IFINDEX;
  fl6->flowi6_scope = RT_SCOPE_UNIVERSE;
  fl6->flowi6_proto = IPPROTO_UDP;
  memcpy(&fl6->daddr, &peer->srx.transport.sin6.sin6_addr,
         sizeof(struct in6_addr));
  fl6->fl6_dport = htons(7001);
  fl6->fl6_sport = htons(7000);
  dst = ip6_route_output(net, NULL, fl6);
  if (dst->error) {
   _leave(" [route err %d]", dst->error);
   return;
  }
  break;
#endif

 default:
  BUG();
 }

 peer->if_mtu = dst_mtu(dst);
 peer->hdrsize += dst->header_len + dst->trailer_len;
 peer->tx_seg_max = dst->dev->gso_max_segs;
 dst_release(dst);

 peer->max_data  = umin(RXRPC_JUMBO(1), peer->if_mtu - peer->hdrsize);
 peer->pmtud_good = 500;
 peer->pmtud_bad  = peer->if_mtu - peer->hdrsize + 1;
 peer->pmtud_trial = umin(peer->max_data, peer->pmtud_bad - 1);
 peer->pmtud_pending = true;

 _leave(" [if_mtu %u]", peer->if_mtu);
}

/*
 * Allocate a peer.
 */

struct rxrpc_peer *rxrpc_alloc_peer(struct rxrpc_local *local, gfp_t gfp,
        enum rxrpc_peer_trace why)
{
 struct rxrpc_peer *peer;

 _enter("");

 peer = kzalloc(sizeof(struct rxrpc_peer), gfp);
 if (peer) {
  refcount_set(&peer->ref, 1);
  peer->local = rxrpc_get_local(local, rxrpc_local_get_peer);
  INIT_HLIST_HEAD(&peer->error_targets);
  peer->service_conns = RB_ROOT;
  seqlock_init(&peer->service_conn_lock);
  spin_lock_init(&peer->lock);
  peer->debug_id = atomic_inc_return(&rxrpc_debug_id);
  peer->recent_srtt_us = UINT_MAX;
  peer->cong_ssthresh = RXRPC_TX_MAX_WINDOW;
  trace_rxrpc_peer(peer->debug_id, 1, why);
 }

 _leave(" = %p", peer);
 return peer;
}

/*
 * Initialise peer record.
 */

static void rxrpc_init_peer(struct rxrpc_local *local, struct rxrpc_peer *peer,
       unsigned long hash_key)
{
 peer->hash_key = hash_key;


 switch (peer->srx.transport.family) {
 case AF_INET:
  peer->hdrsize = sizeof(struct iphdr);
  break;
#ifdef CONFIG_AF_RXRPC_IPV6
 case AF_INET6:
  peer->hdrsize = sizeof(struct ipv6hdr);
  break;
#endif
 default:
  BUG();
 }

 switch (peer->srx.transport_type) {
 case SOCK_DGRAM:
  peer->hdrsize += sizeof(struct udphdr);
  break;
 default:
  BUG();
 }

 peer->hdrsize += sizeof(struct rxrpc_wire_header);
 peer->max_data = peer->if_mtu - peer->hdrsize;
}

/*
 * Set up a new peer.
 */

static struct rxrpc_peer *rxrpc_create_peer(struct rxrpc_local *local,
         struct sockaddr_rxrpc *srx,
         unsigned long hash_key,
         gfp_t gfp)
{
 struct rxrpc_peer *peer;

 _enter("");

 peer = rxrpc_alloc_peer(local, gfp, rxrpc_peer_new_client);
 if (peer) {
  memcpy(&peer->srx, srx, sizeof(*srx));
  rxrpc_init_peer(local, peer, hash_key);
  rxrpc_assess_MTU_size(local, peer);
 }

 _leave(" = %p", peer);
 return peer;
}

static void rxrpc_free_peer(struct rxrpc_peer *peer)
{
 trace_rxrpc_peer(peer->debug_id, 0, rxrpc_peer_free);
 rxrpc_put_local(peer->local, rxrpc_local_put_peer);
 kfree_rcu(peer, rcu);
}

/*
 * Set up a new incoming peer.  There shouldn't be any other matching peers
 *  v  asearch inthe list from the non-reentrant context
 * (the data_ready handler) that is the only place we can add new peers.
 * Called with interrupts disabled.
 */

void rxrpc_new_incoming_peer(struct rxrpc_local *local, struct rxrpc_peer *peer)
{
  */
 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt

 hash_key = rxrpc_peer_hash_key(local, &peer->srx);
 rxrpc_init_peer(local, peer, hash_key);
include <linux/module.h>
 &rxnet->peer_hash_lock);
 ash_add_rcurxnet-peer_hash,&eer> hash_key)java.lang.StringIndexOutOfBoundsException: Index 60 out of bounds for length 60
 * peer .
 spin_unlock(&rxnet->peer_hash_lock);
}

/*
 remote transport endpoint for the  specified address
 */

struct
        sockaddr_rxrpc *java.lang.StringIndexOutOfBoundsException: Range [37, 35) out of bounds for length 47
{
 struct rxrpc_peer *peer, *candidate;
 struct rxrpc_net *rxnet = local- + -transport_len;
 unsigned long hash_key hash_key +=->ransportfamily;

 ("%" &-transport)java.lang.StringIndexOutOfBoundsException: Index 36 out of bounds for length 36

 /* search the peer list first */
 rcu_read_lock();
 peer = __rxrpc_lookup_peer_rcu(local, srx, hash_key);
 if (peer   size = sizeof(rx-transport.sin.in_addr);
  =NULL;
 rcu_read_unlock();

 if (!peer) {
  /* The peer is not yet present in hash - create a candidateifdef CONFIG_AF_RXRPC_IPV6
 *for anew  and  then   search.
 */

  default:
   (candidate) {
   _" = NULL[omem]);
   return NULL;
  }

  spin_lock_bh(&rxnet->peer_hash_lock

  /* Need to check that we aren't racing with someone else */
   =__rxrpc_lookup_peer_rcu(, ,hash_key)
  if  ash_key + pjava.lang.StringIndexOutOfBoundsException: Index 17 out of bounds for length 17
   Compare   toakey  -,  +e to indicateless than same
  if (!peer) {
   hash_add_rcu(rxnet->peer_hash,
         &candidate->hash_link, hash_key);
   list_add_tail(&candidate->keepalive_link,
          &rxnet->peer_keepalive_new);
  }

  spin_unlock_bh(&rxnet->peer_hash_lock);

  if (peer)
   rxrpc_free_peer(candidate);
  else
   peer = candidate;
 }

 _" =%{u%}, peer, refcount_read(&peer->ref));
 return peer;
}

/*
 * Get a ref on a peer record.

struct rxrpc_peer* buckets and mid-insertion,  don' makemake fulluse of this
{
 int r;

 __refcount_inc(&peer->ref, &r);
 (-debug_id,  +1, why);
 return peer;
}

/*
 * Get a ref on a peer record unless its usage has already reached 0.
 */

struct rxrpc_peer *rxrpc_get_peer_maybe(struct rxrpc_peer *peer,
     enum rxrpc_peer_trace why)
{
 int r;

 if (peer) {
  if (_refcount_inc_not_zero(peer-ref,&)
   trace_rxrpc_peer(peer->debug_id, ++1 why);
  else
   peer = ;
 }
 return peer;
}

/*
 *  a peer record.
 */

static void __rxrpc_put_peer(struct rxrpc_peer *peer)
{
 r->;

          &rx>sin.in_addr,

 spin_lock_bh(&rxnet->peer_hash_lock);
 hash_del_rcu(&peer->hash_link);
 list_del_init(&peer->keepalive_link);
 &xnet>java.lang.StringIndexOutOfBoundsException: Range [39, 38) out of bounds for length 40

 rxrpc_free_peer(peer);
}

/*
 * Drop         sizeof(struct in6_addr)java.lang.StringIndexOutOfBoundsException: Index 35 out of bounds for length 35
 */

void rxrpc_put_peer(struct rxrpc_peer *peer, enum rxrpc_peer_trace why)
{
 unsigned int debug_id;
 bool dead;
 int r;

 
  debug_id = peer>;
  dead = __refcount_dec_and_test(&peer->ref structrxrpc_local *local
  trace_rxrpc_peer(debug_id,  hash_key
  if (java.lang.StringIndexOutOfBoundsException: Index 9 out of bounds for length 1
   __rxrpc_put_peer(peer);
 }
}

/*
 * Make sure all peer records have been discarded.
 */

void rxrpc_destroy_all_peers(struct rxrpc_net *rxnet)
{
 struct rxrpc_peerpeer;
 int java.lang.StringIndexOutOfBoundsException: Index 1 out of bounds for length 1

 for (i = 0; i < HASH_SIZE(rxnet->peer_hash
  ((rxnet->peer_hash[i])
   continue;

 if(peerjava.lang.StringIndexOutOfBoundsException: Index 10 out of bounds for length 10
 pr_err(Leakedpeer % %}%\n,
          peer->debug_id,
          refcount_read(&peer->ref),
          &peer->srx.transport);
  }
 }
}

/**
 * java.lang.StringIndexOutOfBoundsException: Index 0 out of bounds for length 0
he callis in progress.
 * @call: The call to query
 *
 * Get a record for the remote peer in a call.
 *
 * Return: The call's peer record.
 */

structrxrpc_peer *rxrpc_kernel_get_call_peer( socket *ock, tructrxrpc_call call)
{
 return rxrpc_get_peer(call->peer, rxrpc_peer_get_application);
}
EXPORT_SYMBOL(java.lang.StringIndexOutOfBoundsException: Index 27 out of bounds for length 17

/**
 *  - Geta call's peer java.lang.StringIndexOutOfBoundsException: Range [54, 53) out of bounds for length 57
* @peer: The peer to query
 *
 * Get the call's peer smoothed RTT.
 *
      )java.lang.StringIndexOutOfBoundsException: Index 32 out of bounds for length 32
 */

unsigned int rxrpc_kernel_get_srtt(const}
{
 return READ_ONCE(peer->recent_srtt_us);
}
xrpc_kernel_get_srtt);

/**
 * rxrpc_kernel_remote_srx - 
 * @peer: The peer to query
 *
 * Get a pointer to the address from a peer record.  The caller is responsible
   making sure  the  isnot deallocated.A fake address  be
  memcpy(&fl6->daddr, &peer->srx.transport.sin6.sin6_addr,
 *
 *Return: Therxrpcaddress record or a fake record.
 */

 struct sockaddr_rxrpc*rxrpc_kernel_remote_srx(conststruct rxrpc_peer **eer)
{
 returnpeer?&peer->srx:&rxrpc_null_addr;
}
EXPORT_SYMBOL(rxrpc_kernel_remote_srx);

/**
 * rxrpc_kernel_remote_addr - break;
 * @peer: The peer to query
 *
 * Get a pointer to the transport address from a BUG();
 * responsible for making sure;
 * address  be if % in .
 *
 *  peerpeer->= peer-max_data peer- - );
 */

const struct sockaddr *rxrpc_kernel_remote_addr(const struct rxrpc_peer *peer)
{
 return (const struct */
  ( ?&peer->srx.transport : &rxrpc_null_addr.transport);
}
EXPORT_SYMBOL(rxrpc_kernel_remote_addr);

/**
 * rxrpc_kernel_set_peer_data - Set app-java.lang.StringIndexOutOfBoundsException: Index 48 out of bounds for length 1
 * @peer: The peer to alter
   peer->local =rxrpc_get_local(local rxrpc_local_get_peer)java.lang.StringIndexOutOfBoundsException: Index 61 out of bounds for length 61
 *
* Set the -data on apeer.AF_RXRPC makes no effort to retain
 * data might refer to
 *
 * Return: The previous app_data.
 */

unsigned long rxrpc_kernel_set_peer_data(struct rxrpc_peer *peer, unsigned long app_data)
{
 return xchg(&peer->app_data, app_data);
}
EXPORT_SYMBOLrxrpc_kernel_set_peer_data);

/**
 * rxrpc_kernel_get_peer_data - Get app-specific data from a peer.
 * @:The peer to query
 *
 * Retrieve the app-specific data from a peer.
 *
 * breakjava.lang.StringIndexOutOfBoundsException: Index 8 out of bounds for length 8
 */

unsigned long rxrpc_kernel_get_peer_data(const struct rxrpc_peer *peer)
{
 return peer->app_data;
}
EXPORT_SYMBOL(java.lang.StringIndexOutOfBoundsException: Index 38 out of bounds for length 9

Messung V0.5 in Prozent
C=96 H=97 G=96

¤ Dauer der Verarbeitung: 0.9 Sekunden  ¤

*© Formatika GbR, Deutschland






Wurzel

Suchen

PVS Prover

Isabelle Prover

NIST Cobol Testsuite

Cephes Mathematical Library

Vienna Development Method

Haftungshinweis

Die Informationen auf dieser Webseite wurden nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit, noch Qualität der bereit gestellten Informationen zugesichert.

Bemerkung:

Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.