1  /** Zone memory management. -*- Mode: ObjC -*-
       2     Copyright (C) 1997,1998,1999 Free Software Foundation, Inc.
       3  
       4     Written by: Yoo C. Chung <wacko@laplace.snu.ac.kr>
       5     Date: January 1997
       6  
       7     This file is part of the GNUstep Base Library.
       8  
       9     This library is free software; you can redistribute it and/or
      10     modify it under the terms of the GNU Lesser General Public
      11     License as published by the Free Software Foundation; either
      12     version 2 of the License, or (at your option) any later version.
      13  
      14     This library is distributed in the hope that it will be useful,
      15     but WITHOUT ANY WARRANTY; without even the implied warranty of
      16     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
      17     Library General Public License for more details.
      18  
      19     You should have received a copy of the GNU Lesser General Public
      20     License along with this library; if not, write to the Free
      21     Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
      22     Boston, MA 02111 USA.
      23  
      24      AutogsdocSource:	NSZone.m
      25      AutogsdocSource:	NSPage.m
      26  
      27     */
      28  
      29  #ifndef __NSZone_h_GNUSTEP_BASE_INCLUDE
      30  #define __NSZone_h_GNUSTEP_BASE_INCLUDE
      31  #import	"../GNUstepBase/GSVersionMacros.h"
      32  
      33  /**
      34   * Primary structure representing an <code>NSZone</code>.  Technically it
      35   * consists of a set of function pointers for zone upkeep functions plus some
      36   * other things-
      37  <example>
      38  {
      39    // Functions for zone.
      40    void *(*malloc)(struct _NSZone *zone, size_t size);
      41    void *(*realloc)(struct _NSZone *zone, void *ptr, size_t size);
      42    void (*free)(struct _NSZone *zone, void *ptr);
      43    void (*recycle)(struct _NSZone *zone);
      44    BOOL (*check)(struct _NSZone *zone);
      45    BOOL (*lookup)(struct _NSZone *zone, void *ptr);
      46  
      47    // Zone statistics (not always maintained).
      48    struct NSZoneStats (*stats)(struct _NSZone *zone);
      49    
      50    size_t gran;    // Zone granularity (passed in on initialization)
      51    NSString *name; // Name of zone (default is 'nil')
      52    NSZone *next;   // Pointer used for internal management of multiple zones.
      53  }</example>
      54   */
      55  typedef struct _NSZone NSZone;
      56  
      57  #import	"NSObjCRuntime.h"
      58  
      59  @class NSString;
      60  
      61  #if	defined(__cplusplus)
      62  extern "C" {
      63  #endif
      64  
      65  struct _NSZone
      66  {
      67    /* Functions for zone. */
      68    void *(*malloc)(struct _NSZone *zone, size_t size);
      69    void *(*realloc)(struct _NSZone *zone, void *ptr, size_t size);
      70    void (*free)(struct _NSZone *zone, void *ptr);
      71    void (*recycle)(struct _NSZone *zone);
      72    BOOL (*check)(struct _NSZone *zone);
      73    BOOL (*lookup)(struct _NSZone *zone, void *ptr);
      74    struct NSZoneStats (*stats)(struct _NSZone *zone);
      75    
      76    size_t gran; // Zone granularity
      77    __unsafe_unretained NSString *name; // Name of zone (default is 'nil')
      78    NSZone *next;
      79  };
      80  
      81  /**
      82   * Creates a new zone of start bytes, which will grow and shrink by
      83   * granularity bytes.  If canFree is 0, memory in zone is allocated but
      84   * never freed, meaning allocation will be very fast.  The whole zone can
      85   * still be freed with NSRecycleZone(), and you should still call NSZoneFree
      86   * on memory in the zone that is no longer needed, since a count of allocated
      87   * pointers is kept and must reach zero before freeing the zone.<br />
      88   * If Garbage Collection is enabled, this function does nothing other than
      89   * log a warning and return the same value as the NSDefaultMallocZone()
      90   * function.
      91   */
      92  GS_EXPORT NSZone*
      93  NSCreateZone (NSUInteger start, NSUInteger gran, BOOL canFree);
      94  
      95  /** Returns the default zone for memory allocation.  Memory created in this
      96   * zone is the same as memory allocates using the system malloc() function.
      97   */
      98  GS_EXPORT NSZone*
      99  NSDefaultMallocZone (void);
     100  
     101  /**
     102   * Searches and finds the zone ptr was allocated from.  The speed depends
     103   * upon the number of zones and their size.<br />
     104   * If Garbage Collection is enabled, this function always returns the
     105   * same as the NSDefaultMallocZone() function.
     106   */
     107  GS_EXPORT NSZone*
     108  NSZoneFromPointer (void *ptr);
     109  
     110  /**
     111   * Allocates and returns memory for elems items of size bytes, in the
     112   * given zone.  Returns NULL if allocation of size 0 requested.  Raises
     113   * <code>NSMallocException</code> if not enough free memory in zone to
     114   * allocate and no more can be obtained from system, unless using the
     115   * default zone, in which case NULL is returned.<br />
     116   * If Garbage Collection is enabled, this function always allocates
     117   * non-scanned, non-collectable memory in the NSDefaultMallocZone() and
     118   * the zone argument is ignored.
     119   */
     120  GS_EXPORT void*
     121  NSZoneMalloc (NSZone *zone, NSUInteger size);
     122  
     123  /**
     124   * Allocates and returns cleared memory for elems items of size bytes, in the
     125   * given zone.  Returns NULL if allocation of size 0 requested.  Raises
     126   * <code>NSMallocException</code> if not enough free memory in zone to
     127   * allocate and no more can be obtained from system, unless using the
     128   * default zone, in which case NULL is returned.<br />
     129   * If Garbage Collection is enabled, this function always allocates
     130   * non-scanned, non-collectable memory in the NSDefaultMallocZone() and
     131   * the zone argument is ignored.
     132   */
     133  GS_EXPORT void*
     134  NSZoneCalloc (NSZone *zone, NSUInteger elems, NSUInteger bytes);
     135  
     136  /**
     137   * Reallocates the chunk of memory in zone pointed to by ptr to a new one of
     138   * size bytes.  Existing contents in ptr are copied over.  Raises an
     139   * <code>NSMallocException</code> if insufficient memory is available in the
     140   * zone and no more memory can be obtained from the system, unless using the
     141   * default zone, in which case NULL is returned.<br />
     142   * If Garbage Collection is enabled, the zone argument is ignored.
     143   */
     144  GS_EXPORT void*
     145  NSZoneRealloc (NSZone *zone, void *ptr, NSUInteger size);
     146  
     147  /**
     148   * Return memory for an entire zone to system.  In fact, this will not be done
     149   * unless all memory in the zone has been explicitly freed (by calls to
     150   * NSZoneFree()).  For "non-freeable" zones, the number of NSZoneFree() calls
     151   * must simply equal the number of allocation calls.  The default zone, on the
     152   * other hand, cannot be recycled.<br />
     153   * If Garbage Collection is enabled, this function has not effect.
     154   */
     155  GS_EXPORT void
     156  NSRecycleZone (NSZone *zone);
     157  
     158  /**
     159   * Frees memory pointed to by ptr (which should have been allocated by a
     160   * previous call to NSZoneMalloc(), NSZoneCalloc(), or NSZoneRealloc()) and
     161   * returns it to zone.  Note, if this is a nonfreeable zone, the memory is
     162   * not actually freed, but the count of number of free()s is updated.<br />
     163   * If Garbage Collection is enabled, the zone argument is ignored and this
     164   * function causes ptr to be deallocated immediately.
     165   */
     166  GS_EXPORT void
     167  NSZoneFree (NSZone *zone, void *ptr);
     168  
     169  /**
     170   * Sets name of the given zone (useful for debugging and logging).
     171   */
     172  GS_EXPORT void
     173  NSSetZoneName (NSZone *zone, NSString *name);
     174  
     175  /**
     176   * Returns the name of the given zone (useful for debugging and logging).
     177   */
     178  GS_EXPORT NSString*
     179  NSZoneName (NSZone *zone);
     180  
     181  #if OS_API_VERSION(GS_API_NONE, GS_API_NONE)
     182  
     183  /** Deprecated ...<br />
     184   * Checks integrity of a zone.  Not defined by OpenStep or OS X.
     185   */
     186  BOOL
     187  NSZoneCheck (NSZone *zone);
     188  
     189  /**
     190   *  <code>NSZoneStats</code> is the structure returned by the NSZoneStats()
     191   *  function that summarizes the current usage of a zone.  It is similar to
     192   *  the structure <em>mstats</em> in the GNU C library.  It has 5 fields of
     193   *  type <code>size_t</code>-
     194   *  <deflist>
     195   *    <term><code>bytes_total</code></term>
     196   *    <desc>
     197   *    This is the total size of memory managed by the zone, in bytes.</desc>
     198   *    <term><code>chunks_used</code></term>
     199   *    <desc>This is the number of memory chunks in use in the zone.</desc>
     200   *    <term><code>bytes_used</code></term>
     201   *    <desc>This is the number of bytes in use.</desc>
     202   *    <term><code>chunks_free</code></term>
     203   *    <desc>This is the number of memory chunks that are not in use.</desc>
     204   *    <term><code>bytes_free</code></term>
     205   *    <desc>
     206   *    This is the number of bytes managed by the zone that are not in use.
     207   *    </desc>
     208   *  </deflist>
     209   */
     210  struct NSZoneStats
     211  {
     212    size_t bytes_total;
     213    size_t chunks_used;
     214    size_t bytes_used;
     215    size_t chunks_free;
     216    size_t bytes_free;
     217  };
     218  
     219  /** Deprecated ...<br />
     220   *  Obtain statistics about the zone.  Implementation emphasis is on
     221   *  correctness, not speed.  Not defined by OpenStep or OS X.
     222   */
     223  struct NSZoneStats
     224  NSZoneStats (NSZone *zone);
     225  
     226  /**
     227   * Try to get more memory - the normal process has failed.
     228   * If we can't do anything, just return a null pointer.
     229   * Try to do some logging if possible.
     230   */
     231  void*
     232  GSOutOfMemory(NSUInteger size, BOOL retry);
     233  
     234  /**
     235   * Called during +initialize to tell the class that instances created
     236   * in future should have the specified instance variable as a weak
     237   * pointer for garbage collection.<br />
     238   * NB. making a pointer weak does not mean that it is automatically
     239   * zeroed when the object it points to is garbage collected. To get that
     240   * behavior you must asign values to the pointer using the
     241   * GSAssignZeroingWeakPointer() function.<br />
     242   * This function has no effect if the system is
     243   * not built for garbage collection.
     244   */
     245  GS_EXPORT void
     246  GSMakeWeakPointer(Class theClass, const char *iVarName);
     247  
     248  /**
     249   * This function must be used to assign a value to a zeroing weak pointer.<br />
     250   * A zeroing weak pointer is one where, when the garbage collector collects
     251   * the object pointed to, it also clears the weak pointer.<br />
     252   * Assigning zero (nil) will always succeed and has the effect of telling the
     253   * garbage collector that it no longer needs to track the previously assigned
     254   * object.  Apart from that case, a source needs to be garbage collectable for
     255   * this function to work, and using a non-garbage collectable value will
     256   * cause the function to return NO.<br />
     257   * If the destination object (the weak pointer watching the source object)
     258   * belongs to a chunk of memory which may be collected before the source
     259   * object is collected, it is important that it is finalised and the
     260   * finalisation code assigns zero to the pointer.<br />
     261   * If garbage collection is not in use, this function performs a simple
     262   * assignment returning YES, unless destination is null in which case it
     263   * returns NO.
     264   */
     265  GS_EXPORT BOOL
     266  GSAssignZeroingWeakPointer(void **destination, void *source);
     267  
     268  #endif
     269  
     270  GS_EXPORT NSUInteger
     271  NSPageSize (void) __attribute__ ((const));
     272  
     273  GS_EXPORT NSUInteger
     274  NSLogPageSize (void) __attribute__ ((const));
     275  
     276  GS_EXPORT NSUInteger
     277  NSRoundDownToMultipleOfPageSize (NSUInteger bytes) __attribute__ ((const));
     278  
     279  GS_EXPORT NSUInteger
     280  NSRoundUpToMultipleOfPageSize (NSUInteger bytes) __attribute__ ((const));
     281  
     282  GS_EXPORT NSUInteger
     283  NSRealMemoryAvailable (void);
     284  
     285  GS_EXPORT void*
     286  NSAllocateMemoryPages (NSUInteger bytes);
     287  
     288  GS_EXPORT void
     289  NSDeallocateMemoryPages (void *ptr, NSUInteger bytes);
     290  
     291  GS_EXPORT void
     292  NSCopyMemoryPages (const void *src, void *dest, NSUInteger bytes);
     293  
     294  #if OS_API_VERSION(MAC_OS_X_VERSION_10_4, OS_API_LATEST)
     295  
     296  enum {
     297    NSScannedOption = (1<<0),
     298    NSCollectorDisabledOption = (1<<1)
     299  };
     300  
     301  /** Allocate memory.  If garbage collection is not enabled this uses the
     302   * default malloc zone and the options are ignored.<br />
     303   * If garbage collection is enabled, the allocate memory is normally not
     304   * scanned for pointers but is itsself garbage collectable.  The options
     305   * argument is a bitmask in which NSScannedOption sets the memory to be
     306   * scanned for pointers by the garbage collector, and
     307   * NSCollectorDisabledOption causes the memory to be excempt from being
     308   * garbage collected itsself.<br />
     309   * In any case the memory returned is zero'ed.
     310   */
     311  GS_EXPORT void *
     312  NSAllocateCollectable(NSUInteger size, NSUInteger options);
     313  
     314  /** Reallocate memory to be of a different size and/or to have different
     315   * options settings.  The behavior of options is as for
     316   * the NSAllocateCollectable() function.
     317   */ 
     318  GS_EXPORT void *
     319  NSReallocateCollectable(void *ptr, NSUInteger size, NSUInteger options);
     320  
     321  #endif
     322  
     323  static inline id NSMakeCollectable(const void *cf) {
     324  #if __has_feature(objc_arc)
     325      return nil;
     326  #else
     327      return (id)cf; // Unimplemented; garbage collection is deprecated.
     328  #endif
     329  }
     330  
     331  #if	defined(__cplusplus)
     332  }
     333  #endif
     334  
     335  #endif /* not __NSZone_h_GNUSTEP_BASE_INCLUDE */