LCOV - code coverage report
Current view: top level - sys - percpu.h (source / functions) Hit Total Coverage
Test: 6.4 Lines: 0 39 0.0 %
Date: 2018-10-19 03:25:38 Functions: 0 8 0.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /*      $OpenBSD: percpu.h,v 1.8 2018/08/28 15:15:02 mpi Exp $ */
       2             : 
       3             : /*
       4             :  * Copyright (c) 2016 David Gwynne <dlg@openbsd.org>
       5             :  *
       6             :  * Permission to use, copy, modify, and distribute this software for any
       7             :  * purpose with or without fee is hereby granted, provided that the above
       8             :  * copyright notice and this permission notice appear in all copies.
       9             :  *
      10             :  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
      11             :  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
      12             :  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
      13             :  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
      14             :  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
      15             :  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
      16             :  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
      17             :  */
      18             : 
      19             : #ifndef _SYS_PERCPU_H_
      20             : #define _SYS_PERCPU_H_
      21             : 
      22             : #ifndef CACHELINESIZE
      23             : #define CACHELINESIZE 64
      24             : #endif
      25             : 
      26             : #ifndef __upunused /* this should go in param.h */
      27             : #ifdef MULTIPROCESSOR
      28             : #define __upunused
      29             : #else
      30             : #define __upunused __attribute__((__unused__))
      31             : #endif
      32             : #endif
      33             : 
      34             : struct cpumem {
      35             :         void            *mem;
      36             : };
      37             : 
      38             : struct cpumem_iter {
      39             :         unsigned int    cpu;
      40             : } __upunused;
      41             : 
      42             : struct counters_ref {
      43             :         uint64_t         g;
      44             :         uint64_t        *c;
      45             : };
      46             : 
      47             : #ifdef _KERNEL
      48             : 
      49             : #include <sys/atomic.h>
      50             : 
      51             : struct pool;
      52             : 
      53             : struct cpumem   *cpumem_get(struct pool *);
      54             : void             cpumem_put(struct pool *, struct cpumem *);
      55             : 
      56             : struct cpumem   *cpumem_malloc(size_t, int);
      57             : struct cpumem   *cpumem_malloc_ncpus(struct cpumem *, size_t, int);
      58             : void             cpumem_free(struct cpumem *, int, size_t);
      59             : 
      60             : void            *cpumem_first(struct cpumem_iter *, struct cpumem *);
      61             : void            *cpumem_next(struct cpumem_iter *, struct cpumem *);
      62             : 
      63             : static inline void *
      64           0 : cpumem_enter(struct cpumem *cm)
      65             : {
      66             : #ifdef MULTIPROCESSOR
      67           0 :         return (cm[cpu_number()].mem);
      68             : #else
      69             :         return (cm);
      70             : #endif
      71             : }
      72             : 
      73             : static inline void
      74           0 : cpumem_leave(struct cpumem *cm, void *mem)
      75             : {
      76             :         /* KDASSERT? */
      77           0 : }
      78             : 
      79             : #ifdef MULTIPROCESSOR
      80             : 
      81             : #define CPUMEM_BOOT_MEMORY(_name, _sz)                                  \
      82             : static struct {                                                         \
      83             :         unsigned char   mem[_sz];                                       \
      84             :         struct cpumem   cpumem;                                         \
      85             : } __aligned(CACHELINESIZE) _name##_boot_cpumem = {                      \
      86             :         .cpumem = { _name##_boot_cpumem.mem }                           \
      87             : }
      88             : 
      89             : #define CPUMEM_BOOT_INITIALIZER(_name)                                  \
      90             :         { &_name##_boot_cpumem.cpumem }
      91             : 
      92             : #else /* MULTIPROCESSOR */
      93             : 
      94             : #define CPUMEM_BOOT_MEMORY(_name, _sz)                                  \
      95             : static struct {                                                         \
      96             :         unsigned char   mem[_sz];                                       \
      97             : } __aligned(sizeof(uint64_t)) _name##_boot_cpumem
      98             : 
      99             : #define CPUMEM_BOOT_INITIALIZER(_name)                                  \
     100             :         { (struct cpumem *)&_name##_boot_cpumem.mem }
     101             : 
     102             : #endif /* MULTIPROCESSOR */
     103             : 
     104             : #define CPUMEM_FOREACH(_var, _iter, _cpumem)                            \
     105             :         for ((_var) = cpumem_first((_iter), (_cpumem));                 \
     106             :             (_var) != NULL;                                             \
     107             :             (_var) = cpumem_next((_iter), (_cpumem)))
     108             : 
     109             : /*
     110             :  * per cpu counters
     111             :  */
     112             : 
     113             : struct cpumem   *counters_alloc(unsigned int);
     114             : struct cpumem   *counters_alloc_ncpus(struct cpumem *, unsigned int);
     115             : void             counters_free(struct cpumem *, unsigned int);
     116             : void             counters_read(struct cpumem *, uint64_t *, unsigned int);
     117             : void             counters_zero(struct cpumem *, unsigned int);
     118             : 
     119             : static inline uint64_t *
     120           0 : counters_enter(struct counters_ref *ref, struct cpumem *cm)
     121             : {
     122           0 :         ref->c = cpumem_enter(cm);
     123             : #ifdef MULTIPROCESSOR
     124           0 :         ref->g = ++(*ref->c); /* make the generation number odd */
     125           0 :         membar_producer();
     126           0 :         return (ref->c + 1);
     127             : #else
     128             :         return (ref->c);
     129             : #endif
     130             : }
     131             : 
     132             : static inline void
     133           0 : counters_leave(struct counters_ref *ref, struct cpumem *cm)
     134             : {
     135             : #ifdef MULTIPROCESSOR
     136           0 :         membar_producer();
     137           0 :         (*ref->c) = ++ref->g; /* make the generation number even again */
     138             : #endif
     139           0 :         cpumem_leave(cm, ref->c);
     140           0 : }
     141             : 
     142             : static inline void
     143           0 : counters_inc(struct cpumem *cm, unsigned int c)
     144             : {
     145           0 :         struct counters_ref ref;
     146             :         uint64_t *counters;
     147             : 
     148           0 :         counters = counters_enter(&ref, cm);
     149           0 :         counters[c]++;
     150           0 :         counters_leave(&ref, cm);
     151           0 : }
     152             : 
     153             : static inline void
     154           0 : counters_dec(struct cpumem *cm, unsigned int c)
     155             : {
     156           0 :         struct counters_ref ref;
     157             :         uint64_t *counters;
     158             : 
     159           0 :         counters = counters_enter(&ref, cm);
     160           0 :         counters[c]--;
     161           0 :         counters_leave(&ref, cm);
     162           0 : }
     163             : 
     164             : static inline void
     165           0 : counters_add(struct cpumem *cm, unsigned int c, uint64_t v)
     166             : {
     167           0 :         struct counters_ref ref;
     168             :         uint64_t *counters;
     169             : 
     170           0 :         counters = counters_enter(&ref, cm);
     171           0 :         counters[c] += v;
     172           0 :         counters_leave(&ref, cm);
     173           0 : }
     174             : 
     175             : static inline void
     176           0 : counters_pkt(struct cpumem *cm, unsigned int c, unsigned int b, uint64_t v)
     177             : {
     178           0 :         struct counters_ref ref;
     179             :         uint64_t *counters;
     180             : 
     181           0 :         counters = counters_enter(&ref, cm);
     182           0 :         counters[c]++;
     183           0 :         counters[b] += v;
     184           0 :         counters_leave(&ref, cm);
     185           0 : }
     186             : 
     187             : #ifdef MULTIPROCESSOR
     188             : #define COUNTERS_BOOT_MEMORY(_name, _n)                                 \
     189             :         CPUMEM_BOOT_MEMORY(_name, ((_n) + 1) * sizeof(uint64_t))
     190             : #else
     191             : #define COUNTERS_BOOT_MEMORY(_name, _n)                                 \
     192             :         CPUMEM_BOOT_MEMORY(_name, (_n) * sizeof(uint64_t))
     193             : #endif
     194             : 
     195             : #define COUNTERS_BOOT_INITIALIZER(_name)        CPUMEM_BOOT_INITIALIZER(_name)
     196             : 
     197             : #endif /* _KERNEL */
     198             : #endif /* _SYS_PERCPU_H_ */

Generated by: LCOV version 1.13