From owner-freebsd-current@FreeBSD.ORG Wed Feb 7 08:41:40 2007 Return-Path: X-Original-To: current@freebsd.org Delivered-To: freebsd-current@FreeBSD.ORG Received: from mx1.freebsd.org (mx1.freebsd.org [69.147.83.52]) by hub.freebsd.org (Postfix) with ESMTP id B4F7B16A400 for ; Wed, 7 Feb 2007 08:41:33 +0000 (UTC) (envelope-from rizzo@icir.org) Received: from xorpc.icir.org (xorpc.icir.org [192.150.187.68]) by mx1.freebsd.org (Postfix) with ESMTP id A397313C4B4 for ; Wed, 7 Feb 2007 08:41:32 +0000 (UTC) (envelope-from rizzo@icir.org) Received: from xorpc.icir.org (localhost [127.0.0.1]) by xorpc.icir.org (8.12.11/8.13.6) with ESMTP id l178fV2p062396; Wed, 7 Feb 2007 00:41:31 -0800 (PST) (envelope-from rizzo@xorpc.icir.org) Received: (from rizzo@localhost) by xorpc.icir.org (8.12.11/8.12.3/Submit) id l178fVtA062395; Wed, 7 Feb 2007 00:41:31 -0800 (PST) (envelope-from rizzo) Date: Wed, 7 Feb 2007 00:41:31 -0800 From: Luigi Rizzo To: current@freebsd.org Message-ID: <20070207004131.A62183@xorpc.icir.org> Mime-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline User-Agent: Mutt/1.2.5.1i Cc: Subject: C macro to find the next power of 2 ? X-BeenThere: freebsd-current@freebsd.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: Discussions about the use of FreeBSD-current List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Wed, 07 Feb 2007 08:41:40 -0000 This is any good as any of our lists to ask, but since it came up while looking at device drivers, i thoght that maybe someone has an answer here... My problem is that some hardware wants data structures aligned to the next power of 2 with respect to their size, and the code in question (the ehci driver in case you care) has hardwired constants for this, and possibly wrong ones. It would be nice if one could write struct foo_desc { ... }; #define FOO_ALIGN next_power_of_2(sizeof(struct foo_desc)) instead of having to count fields and make guesses on the size of pointers and so on. One way i have come up with is the following: #define b2(x) ( (x) | ( (x) >> 1) ) #define b4(x) ( b2(x) | ( b2(x) >> 2) ) #define b8(x) ( b4(x) | ( b4(x) >> 4) ) #define b16(x) ( b8(x) | ( b8(x) >> 8) ) #define b32(x) (b16(x) | (b16(x) >>16) ) #define next_power_of_2(x) (b32(x-1) + 1) Basically if i is the first bit set in x, macro b2 makes sure that 2 bits (i and i-1) are set, macro b4..b32 do the same for up to 32 bits. The offsets -1 in the call to b32() are just to handle the case when x is already a power of 2, and the final +1 produces the result. But i was wondering if there is some simpler code which can still be computed as a compile-time constant ? cheers luigi